在学习装箱和折箱之前,我觉得有必要介绍一下C#中的"值类型"和"引用类型",以下观点仅是个人学习心得和体会,不足之处多多指教~~! 先说一下C#中的"值类型"和"引用类型",这个先要从C#的原理中才好理解: 值类型: 它的数据存储在内存中的堆栈中,每个变量或程序都有自己的堆栈,不可以共用一个堆栈地址。当数据一个值类型的变量传递到另一个相同类型的变量时,会在堆栈中分配两个不同的地址。 值类型数据: 所有数字数据类型 引用类型:它的数据存储在内存中的堆中,可以不同的变量或程序共同使用同一个位置的数据。当数据从一个引用类型的变量传递到另一个相同类型的变量时,只是把这个变量的引用地址传递给新的变量,同时引用当前堆中存储的数据。 引用类型数据: String 总结性的一句话:可以将引用类型指派给 Object 数据类型的变量,Object 变量总是持有指向数据的指针,从不持有数据本身。然而,如果将值类型指派给 Object 变量,则 Object 变量将表现得像持有自己的数据一样。 例子是最能说明问题的: /// <summary> /// <summary> static void Main(string[] args) strPerson sp1 = new strPerson(); 在引用类型中,改变其中一个的值,另一个也会跟差改变,因为他们都是引用的同一个内存地址, 在值类型中,改变其中一个的值,另一个不会变,因为在创建的时候,他们分别有了不同的内存地址。 但是要注意一种情况,如下示例: string a = "this is string a"; 或: Object a = 10; 这里的b不是指向a的地址,而是重新开了另一个内存空间,所以这里显示的结果a和b是绝对不相同的! 这个地方为什么会产生这样的结果还不是很明白,等明白了再补上~~ 明白了引用类型和值类型这后,对了装箱和折箱就简单得多了, 装箱:是把值类型转为引用类型,如: int a = 10; 在这个装箱的过程中,有以下动作:1)划分堆栈内存,在堆栈上分配的内存 = a的大小 +b及其结构所占用的空间;(2)a被复制到新近分配的堆栈中;(3)将分配给b的地址压栈,此时它指向一个object类型,即引用类型。 折箱则相反,把引用类型转为值类型,如: object c = 5; 在这个折箱的过程中,有以下动作:1)环境须先判断堆栈上指向合法对象的地址,以及在对此对象向指定的类型进行转换时是否合法,如果不合法,就抛出异常;(2)当判断类型转换正确,就返回一个指向对象内的值的指针。 |