• 拆箱跟装箱内存分配与数据拷贝


    拆箱跟装箱内存分配与数据拷贝
    demo1:
    int i=100;
    object o=i;
    i=200;
    在这个实例中,程序执行了一个装箱操作。CLR为对象o在GC堆上分配了一块内存区,并把i中的数据100拷贝到了o的内存块中。注意:这里是拷贝,不是搬移,所以在Stack上还是有一块内存存储着i的。当执行到i=200的时候,所改变的是Stack上i的值,而GC堆上o的值并没有被改变。
    这个实例可能比较好理解,再看下面的实例。
    demo2:
    int i=100;
    object o=i;
    object a=o;
    a=300;
    这里程序执行了两个装箱操作。第一次:object o=i;第二次:a=300;
    这个实例前面两条语句好理解了。object a=o;这时CLR并没有为a分配内存块(因为object 是引用类型),CLR只是返回了一个指针指向了a所指向的那块内存(o和a其实都只是一个指针而已)。当执行到a=300;的时候,这是第二次装箱,前面说过了,装箱是数据拷贝,所以此时CLR会分配一块内存块,把300这个值放到这个内存块中,并且把a的指针更改,指向300这块内存。可以看出,此时o跟a是指向了不同的内存块了。GC.ReferenceEquals(o, a);返回的是false;
    到这里可能也还好理解,在看下面的实例。
    demo3:
    public class Class1
    {
       public int i;
    }

    static void Main()
    {
       Class1 class1=new Class1();
       class1.i=100;
       Class2 class2=class1;
       class2.i=200;
       class2=null;
    }
    在这个实例中,程序没有执行任何的装箱操作。因为Class1这个类型中的i是一个值类型的,这个要注意:值类型并非都是分配在Stack上的,这里所说的值类型是一个引用类型中的值类型。它是分配在GC堆上的,程序中class1跟class2是指向同一块内存区的,它们所做的操作都是对这块内存区中的数据进行操作。所以最终i的值是被class2更改为200了。
  • 相关阅读:
    hihoCoder #1078 : 线段树的区间修改
    hihoCode r#1077 : RMQ问题再临-线段树
    hihoCoder #1070 : RMQ问题再临
    hihoCoder #1068 : RMQ-ST算法(模板)
    LeetCode Valid Sudoku 有效数独
    150 Evaluate Reverse Polish Notation 逆波兰表达式求值
    149 Max Points on a Line 直线上最多的点数
    148 Sort List 链表上的归并排序和快速排序
    147 Insertion Sort List 链表插入排序
    146 LRU Cache 最近最少使用页面置换算法
  • 原文地址:https://www.cnblogs.com/bmrxntfj/p/818243.html
Copyright © 2020-2023  润新知