垃圾回收器检查托管堆中是否有应用程序不再使用的任何对象。如果有,它们使用的内存就可以回收(如果一次垃圾回收之后,堆中仍然没有可用的内存,new操作符将会抛出一个OutOfMemoryException)。垃圾回收期如何知道应用程序正在使用一个对象?你或许已经想到,这不是一个三言两语就能说清楚的问题。
每个应用程序都包含一组根(root)。每个根都是一个存储位置,其中包含指向引用类型对象的一个指针。该指针要么引用托管堆中的一个对象,要么为NULL 。例如,类型中定义个任何静态字段都认为是一个根。除此以外,任何方法参数或局部变量也被认为是一个根。只有引用类型的变量才被认为是根;值类型的变量用不用不被认为是根。让我们看一个具体的例子,首先是类定义:
internal sealed class SomeType{
private TextWriter m_textWriter;
public SomeType(TextWriter tw){
m_textWriter = tw;
}
public void WriteBytes(Byte[] bytes){
for(Int 32 x=0; x< bytes.Length; x ++)
{
m_textWriter.Write(bytes[x]);
}
}
}
WriteBytes 方法第一次调用时,JIT编译器将方法的IL代码转换成本地CPU指令。假定CLR在一个x86 CPU上运行,JIT编译器将WriteBytes方法编译成CPU指令。
JIT编译器生成本地代码时,还会创建一个内部使用的表。从逻辑上来讲,该表中的每个记录项都代表在方法的本地CPU至灵中的一个字节偏移范围。针对这个范围,这个记录项都记录了包含着根的一组内存地址和CPU寄存器。