什么时候变量的空间在堆栈上分配?

时间:2011-04-12 21:28:07

标签: c#

在声明或初始化期间分配空间:

int c; // here

c = 5; // or here

4 个答案:

答案 0 :(得分:12)

  

何时在堆栈上分配变量的空间?

您的问题预先假定变量的存储在堆栈上分配。它不一定是。你刚才说“int a;”不指示那是局部变量还是字段,并且没有指示其他重要信息,例如局部变量是否是匿名函数的封闭本地,或者块是否是迭代器块。在许多情况下,变量不会消耗堆栈空间,因为变量不是短暂的。

假设为了参数,变量是一个短暂的局部变量。它仍然可能不在堆栈中。它可能已被注册,特别是如果抖动知道它位于具有大量未使用寄存器的架构上。

假设为了参数,变量是一个短暂的局部变量,并且抖动没有选择注册它,何时分配了堆栈空间?

嗯,再次,你假设抖动使用堆栈作为临时池;虽然这是一种方便的数据结构,但抖动允许宽幅度。临时池可以从堆中分配,也可以有多个堆栈;一些体系结构支持将数据堆栈与调用堆栈分离,以防止堆栈粉碎攻击。

假设变量是一个短暂的局部变量,并且抖动选择不注册它,并且临时池在调用堆栈上,何时分配它的堆栈空间?

那么现在它取决于“分配”的含义。整个百万字节的堆栈在虚拟内存系统中保留并积极提交,因此答案是“一旦创建了线程,就会分配此线程中堆栈中所有内容的堆栈空间,并保留分配“。当然它在页面文件中保持分配。在页面错误从磁盘上的页面文件中引入之前,该堆栈不会移动到硬件(RAM)中。

如果您要问的是“堆栈指针何时被撞击以便有特定的堆栈空间可用于此局部变量”,那么答案通常是“一旦控制进入方法”。这样做当然可以触发我刚才提到的页面错误。

我很想知道你为什么关心。它有什么不同?

答案 1 :(得分:1)

首先,要清除每次在Stack内存上分配值类型的混淆,请阅读以下链接。

引用下面的文章:

“人们解释了价值类型和引用类型之间的差异已经造成了很多混乱,因为”值类型在堆栈上,引用类型在堆上“。这完全是不真实的(如上所述)和本文试图在某种程度上澄清问题。“

memory allocation of value types and reference types in .net framework

http://www.yoda.arachsys.com/csharp/memory.html

http://msdn.microsoft.com/en-us/magazine/cc163791.aspx

答案 2 :(得分:0)

在创建线程时分配堆栈,然后按需扩展,可能以堆栈溢出结束。

答案 3 :(得分:-2)

编辑:啊,我现在看到这是专门引用堆栈内存的。我的回答解决堆内存问题。不过,我会为子孙后代保留它。

我很确定它是在初始化期间,就好像你有一个像

这样的对象
IEnumerable<String> myVariable;

你可以做到:

myVariable = new List<String>();

你还可以这样做:

myVariable = new Stack<String>();

更重要的是,你可以让自己的类充满大量需要大量内存的元数据,只要你正确地实现IEnumerable,你就可以这样做:

myVariable = new MyIEnumerableClass<String>();

因此,(在一般意义上)直到变量被初始化,没有办法实际知道需要多少内存。