例如:
public void Cleanup()
public void Shutdown()
……
你可以这么做,但是有一个标准的名字
public void Dispose()
甚至有一个接口IDisposeable,里面包含的就是刚才那个方法
public interface IDisposable
{
void Dispose()
}
因此最好的办法是让你的类去实现IDisposable接口,在接口内的Dispose方法内提供一段清除非托管资源的代码。
public void Dispose()
{
//这里释放一个句柄(句柄是一个非托管资源,属于Win32编程的概念)
Win32.DestroyHandle(this.CursorFileBitmapIconServiceHandle);
}
OK。这就完成了,除非你想做的更好!
2.3、别忘了类中的托管资源还占着空间!
托管资源占着空间?你首先想到的可能是那些int,string等等这些托管资源,它们能占用几个空间,他们占着就占着呗!
但是托管资源可不仅仅是那些资源,要是你的对象使用了250MB的System.Drawing,Bitmap(这是在.Net Frame中的,属于托管资源)作为一些缓冲怎么办?当然,你知道这是一个.Net的托管资源,所以GC理所应当的将会释放它。但是你真的想留着250MB的内存空间就那么被占用着?然后等待着GC最终释放它?更或者要是有一个更大数据库连接呢?我们当然不想让那连接白白占用来等待GC的终结!
如果用户调用了Dispose方法(意味着他们不再想使用这个对象里的一切)为什么不去扔掉那些浪费空间的位图资源和数据库连接呢?
那么,我们就应该这么做:
释放非托管资源(因为我们必须这么做) 释放托管资源(让你的Dispose更完美)所以,让我们更新我们的Dispose方法来释放那些托管资源
public void Dispose()
{
//Free unmanaged resources
Win32.DestroyHandle(this.CursorFileBitmapIconServiceHandle);
//Free managed resources too
if (this.databaseConnection !=null)
{
this.databaseConnection.Dispose();
this.databaseConnection =null;
}
if (this.frameBufferImage !=null)
{
this.frameBufferImage.Dispose();
this.frameBufferImage = null;
}
}
OK,做的很好了,除非你想做的更好!
2.4、总会有人粗心忘记调用Dispose!
要是有人使用你的类创建了对象,但是忘记调用Dispose方法该怎么办?这将会泄露一些非托管的资源!
注意:忘记调用Dispose方法虽然会造成非托管资源的泄露,但是对于那些托管资源来说,是不会泄露的,因为最终GC会行动起来,在后台线程中释放那些和托管资源有关的内存空间。这包括你创建的对象和其中的托管资源(例如Bitmap和数据库连接) (为什么?往下看)
也就是说,如果你忘记调用Dispose方法,这个类应该自动进行一些补救措施!我们可以想到设计一种方法来做为一种后备方法:利用GC最终调用的终结器










