C# 使用析构函数/处理基类?

C# 使用析构函数/处理基类?,c#,dispose,destructor,idisposable,finalizer,C#,Dispose,Destructor,Idisposable,Finalizer,在C#中,正如和的公认答案中提到的,声明类不继承其父类的析构函数 问题: 如果我想确保释放基类的私有元素,那么在所有子类中实现IDisposable的正确方法是什么?在dispose方法中,调用base.dispose() 这样做看起来没问题,但我更喜欢一种不需要在所有子类中实现的方法。声明对基类自动调用析构函数。您应该遵循此处的说明。它也迎合了继承 这里有趣的部分是“析构函数不继承”,我不知道该怎么理解它。我编写了一个小测试,但让我松了一口气的是,您只需要在基类中编写一个析构函数 因此,子类与

在C#中,正如和的公认答案中提到的,声明类不继承其父类的析构函数

问题: 如果我想确保释放基类的私有元素,那么在所有子类中实现IDisposable的正确方法是什么?在dispose方法中,调用base.dispose()

这样做看起来没问题,但我更喜欢一种不需要在所有子类中实现的方法。

声明对基类自动调用析构函数。

您应该遵循此处的说明。它也迎合了继承

这里有趣的部分是“析构函数不继承”,我不知道该怎么理解它。我编写了一个小测试,但让我松了一口气的是,您只需要在基类中编写一个析构函数

因此,子类与基类非托管资源是不耦合的。他们可以覆盖
Dispose(bool)
来清理自己的事务

但是我做了一个评论,因为我看到太多的程序员实现完整模式只是为了处理托管资源


从一般设计的角度来看,一次性类最好是密封的

基类应该使用for基类-这样,只有基类需要终结器,而派生类只需重写虚方法

protected void Dispose(bool disposing)

如果父类使用Microsoft的IDisposable模式,则子类不应重写Dispose(void),而应重写Dispose(Boolean Disposing)。如果使用Disposing true调用,则它应该处理子类并调用base.dispose(true)。如果使用Disposing false调用,则在大多数情况下,除了call base.Dispose(false)之外,它应该什么都没有


请注意,在大多数情况下,对base.Dispose(False)的调用不会起任何作用,但无论如何都应该进行调用。如果子类需要添加额外的“非托管资源”(即,如果它有需要在终结器中执行的额外职责),它通常应该将这些职责封装到另一个对象中。请注意,类是否具有终结器的问题不仅仅是“实现细节”;将终结器添加到基类可能是一个破坏性的更改,导致一个程序泄漏资源(很糟糕,但如果该程序一次运行时间不太长,则可能可以生存),而在随机情况下,该程序将尝试清理仍在使用的资源(通常不会导致问题,但可能会导致罕见但立即的故障)。

请仅在“私有元素”是非托管资源时执行此操作。@Henk:“私有元素”是否基类的非托管部分是子类不应该真正关心的实现细节。如果您的基类实现了
IDisposable
,那么它应该被释放。在这种情况下,基类的私有元素确实是非托管资源,但正如LukeH所说,子类没有“意识到”这一点。@LukeH:实现IDisposable和必须被释放与拥有(需要)析构函数是分开的。@LukeH:如果一个类或其父类实现了终结器,那么它和所有派生类在许多情况下都可能必须使用GC.KeepAlive,否则就不必使用它(否则可能导致随机失败)。这不是私有的“实现细节”。如果.net提供了一种标记类的方法,要求抖动始终将“self”视为活动的,那么终结问题可能会被抽象掉,但我不知道有任何这样的方法。谢谢Nik!我应该读到比“析构函数不能被继承或重载”更深入的内容。“谢谢亨克。我会将你链接的模式与我所做的进行比较,并进行必要的调整,只是为了正确!:-D