IDispospos GC.SuppressFinalize(this)位置

我为我的代码使用默认的IDisposable实现模板(模式)。

片段:

public void Dispose() { Dispose(true); GC.SuppressFinalize(this); } protected virtual void Dispose(bool isDisposing) { if (!this.disposed) { if (isDisposing) { //cleanup managed resources } //cleanup unmanaged resources this.disposed = true; } } 

我的问题:为什么在Dispose公共方法中调用“GC.SuppressFinalize(this)”? 在处置受管资源之后,我会在受保护方法的“if(isDisposing)”部分中放置“GC.SuppressFinalize(this)”。

像这样:

 protected virtual void Dispose(bool isDisposing) { if (!this.disposed) { if (isDisposing) { //cleanup managed resources GC.SuppressFinalize(this); } //cleanup unmanaged resources this.disposed = true; } } 

我想它是模板设计模式的一个明显案例。

您的抽象类旨在处理所需的所有重要/必要任务(此处为GC.SuppressFinalize(this)),并允许派生类仅覆盖代码的某些部分。

这里有2个案例:
在Dispose中,Snippet 1,SuppressFinalize
Snippet 2,SuppressFinalize,在Dispose中(true)

在这里,Snippet 1确保始终执行GC.SuppressFinalize。 在代码片段2中,由于派生类的支配而使GC.SuppressFinalize的执行成为可能。

因此,通过在Dispose方法中放置GC.SuppressFinalize,您作为类的设计者将始终确保无论派生类编写的代码如何,都将执行GC.SuppressFinalize。

这只是在Dispose中编写SuppressFinalize而不是Dispose(true)的好处。

Dispose(bool isDisposing)方法不是IDisposable接口的一部分。

您通常会从Dispose方法调用Dispose(true) ,并从终结器调用Dispose(false) ,作为尚未处理对象的回退。

调用SuppressFinalize告诉GC,不需要调用对象的终结器,大概是因为调用Dispose时所有的清理工作都已完成。

如果你的class级没有终结器,那么你根本不需要调用SuppressFinalize ,因为没有终结器可以抑制!

Joe Duffy 在处理,定型,垃圾收集等方面有一些很好的指导 。

我认为任何一种布局都可以选择,但可能他们想强调“在此方法中放置所有释放代码”在受保护的Dispose方法中,因此他们将其他工件处理(抑制终结)放在别处。

另外,假设一个派生类有另一个原因来调用受保护的Dispose方法,但仍然希望最终化发生(出于任何想象的原因,我不知道)。

原因.Dispose是当托管代码(您的代码)处置对象从而选择退出完成时。 人们通常会通过终结者创建另一条进入Dispose(bool处理)的路线,并且该调用对于终结者来说没有任何意义。

这个想法是你的清理代码应该只被调用一次。 但是有两个入口点: Dispose方法和对象终结器。 调用Dispose ,您选择退出finalization,以便只调用一次清理代码。 这里的代码可能会更好地说明它。

引用:

 // NOTE: Leave out the finalizer altogether if this class doesn't // own unmanaged resources itself, but leave the other methods // exactly as they are.