垃圾回收器的工作原理
当对象不再被引用时,对象销毁分两步走,过程如下:
1.CLR执行清理工作,可以定一个析构器来加以控制
2.CLR将对象占用的内存归还给堆 ,解除对象内存分配。对这个阶段你没有控制权。
垃圾回收器在它自己的线程中运行,而且只在特定的时候才会执行。它运行时,应用程序中运行的其他线程将暂停。这是由于垃圾回收器可能需要移动对象并更新对象引用。如果对象仍在使用,这些操作就无法执行。
编写析构器
使用析构器(destructor),可在对象被垃圾回收时执行必要的清理。
使用场景:
1.如果托管资源很大(比如一个多维数组),就可以考虑将该资源的所有引用都设为null,使资源能被立即清理。
2.对象引用了非托管资源(无论直接还是间接),析构器就更有用了。间接的非托管资源,如文件流、网络连接、数据库连接和其他由Windows操作系统管理的资源。
析构器的语法:先写一个~符号,再添加类名。
析构器的限制:
1.只适用于引用类型。
2.不能为析构器指定访问修饰符。这是由于永远不在自己的wack调用析构器,总是由垃圾回收器帮你调用
3.析构器不能获取任何参数。这同样是由于永远不由你自己调用。
资源管理
使用try...finally语句
TextReader reader = new StreamReader(filename);
try
{
string line;
while((line = reader.ReadLine()) != null)
{
Console.WriteLine(line);
}
}
finally
{
reader.close();
}
使用using语句和IDisposable接口
using语句提供了一个脉络清晰的机制来控制资源的生存期。可创建一个对象,此对象在using语句块结束时销毁。
using(type variable = initialization)
{
statementBlock
}
using语句声明的变量的类型必须实现IDisposable接口。
析构器中调用Dispose方法
定自己的类时,如何保证资源得到释放呢?你可以使用:
1.实现IDisposable接口,使用using语句
2.自定义析构器
3.实现IDisposable接口,自定义析构器,在析构器中调用Dispose方法。
class Example : IDisposable
{
private Resource scarce;
private bool disposed = false;
~Example()
{
this.Dispose(false);
}
public virtual void Dispose()
{
this.Dispose(true);
GC.SuppressFinalize(this);
}
protected virtual void Dispose(bool disposing)
{
if (!this.disposed)
{
if (disposing)
{
}
this.disposed = true;
}
}
public void SomeBehaviro()
{
checkIfDisposed();
}
private void checkIfDisposed()
{
if (this.disposed)
{
throw new ObjectDisposedException("示例:对象已经清理");
}
}
}