什么时候处理方法不被调用?

SwD*_*n81 7 c# garbage-collection dispose idisposable finalizer

前几天我正在阅读这篇文章,并想知道为什么有一个Finalizer和Dispose方法.我在这里读到为什么你可能想要将Dispose添加到Finalizer.我的好奇心是,什么时候会调用终结器本身的Dispose方法呢?是否有代码示例,或者它是基于软件运行的系统上发生的事情?如果是这样,可能会发生GC没有运行Dispose方法的情况.

Nol*_*rin 10

此处终结器的目的仅仅是针对内存泄漏的安全预防措施(如果您没有Dispose明确调用).这也意味着如果您希望在程序关闭时释放资源,则不必处置对象,因为GC将被强制完成并收集所有对象.

作为一个相关点,当从终结器中这样做时,以稍微不同的方式处理对象是很重要的.

~MyClass()
{
    Dispose(false);
}

public void Dispose()
{
    Dispose(true);
    GC.SuppressFinalize(this);
}

protected void Dispose(disposing)
{
    if (!this.disposed)
    {
        if (disposing)
        {
            // Dispose managed resources here.
        }
        // Dispose unmanaged resources here.
    }
    this.disposed = true;
}
Run Code Online (Sandbox Code Playgroud)

希望在终结器中配置托管资源的原因是您实际上会在这样做时创建对它们的强引用,这可能会阻止GC正确地执行它并收集它们.当然,应该始终明确地关闭/处置非托管资源(例如Win32句柄等),因为CLR不了解它们.

  • 对于一个终结器尝试取消订阅它所订阅的事件的对象是没用的.终结器运行的唯一方法是,持有订阅的对象是否有资格进行垃圾收集,在这种情况下订阅将没有实际意义. (2认同)

Ree*_*sey 5

这主要是为了保护自己。您无法规定您班级的最终用户将做什么。通过在 Dispose 方法之外提供终结器,GC 将“处置”您的对象,适当地释放您的资源,即使用户忘记调用 Dispose() 或误用您的类。