另一个常见的操作就是类型的赋值操作,即变量之间的赋值。由于值类型和引用类型的变量内部存放的内容不同,导致在变量赋值的时候,会有相同的行为而有不同的结果。
值类型
请看如下代码:
private void SomeMethod()
{
int i, j;
i = 5;
j = i;
j = 10;
}
相信大家一定都知道最后的结果是 i:5, j:10。不过在 .NET中, int类型也是一个结构,不但可以存放整数值,还有一系列的方法和属性可以使用,而非我们以前学 C语言时的那种单纯 int存放一个整数的概念。所以我们现在看针对 int的代码,其实也是在看针对 struct类型的代码。
对于值类型的赋值语句“ j = i”,请看图 -3:
在执行 j = i;语句时,变量 i中的内容被复制了一份,然后放到了变量 j中,此时变量 i和 j都有一个值为 5,同时也可以看出, i和 j的值现在互不相干,完全独立,所以任意修改其中的某个变量的值,不会影响到另外一个。引用类型
请看如下代码:
private void SomeMethod()
{
MyClass x, y;
x = new MyClass();
y = x;
}
代码中先对 x进行了实例化,然后将 x赋值到 y,这段代码的结果请看图 -4:
当执行 y = x;代码时,变量 x中的内容同样复制了一份,然后放到了变量 y之中,但是因为变量 x中存放是一个类型实例(对象)的引用,因此这次赋值操作等同于把这个引用传递给了变量 y,结果就是 x和 y中的引用指向堆中同一个类型的实例(对象)。
你可以使用 x的引用去修改 MyClass实例(对象),然后用 y的引用得到修改后的 MyClass实例(对象),反之亦可,因为 x和 y引用的是同一个实例(对象)。
复杂类型的内存布局概述
以上内容是以值类型或者引用类型为一个整体叙述值类型和引用类型的变量声明和赋值的情况。下面我们看看值类型和引用类型内部含有其他类型成员变量(一般称为字段)的情况。虽然看起来情况似乎复杂了一点,但是只要我们可以把握住值类型的值存放在值类型变量内部,而引用类型的值在堆中存放,引用类型的变量只存放对它实例(对象)的引用这个原则,就可以很清晰的做出分析。