通常来说,变量的值分配的位置与声明该变量的位置有关。局部变量的值总是在线程栈上,实例变量的值则和实例本身一起存储在实例存储的地方。引用类型实例和静态变量总是存储在堆上。
值类型也有可能分配在托管堆上:
这些特殊的情况包括数组中的元素﹑引用类型中的值类型字段﹑迭代器块中的局部变量﹑闭包情况下匿名函数(lamda)中的局部变量。
这是由于在这几种情况下的值类型实例如果分配在线程栈上,有可能会出现线程栈中的方法已经调用结束,但是还会访问这些值的情况。也就是说如果分配在线程栈上,有可能会随着被调用的方法的返回而被清除掉。因此它们也被分配在了托管堆上,以满足在方法返回之后还能够被访问的需要。
单纯的说“引用类型保存在托管堆上,值类型保存在线程栈上”是不准确的。
引用类型的确总是分配在托管堆上,但是值类型并非总是分配在线程栈上。