0

关于如何Dispose Pattern完全正确使用的简短问题。我在我的 Dispose 方法中处理托管资源。

但是,不是一次性的物品呢?喜欢或或...StringSystem.Text.Decoder

我如何正确处理这些对象。如果我不将它们设置为null如果我不让 GC 最终确定它们会发生GC.SupressFinalize(this);什么?

这是我如何实现模式的示例:

  private class RequestState : IDisposable {
    const int BufferSize = 1024;
    public StringBuilder RequestData;
    public byte[] BufferRead;
    public WebRequest Request;
    public Stream ResponseStream;
    // Create Decoder for appropriate enconding type.
    public Decoder StreamDecode = Encoding.UTF8.GetDecoder();
    public MyMamespace.Machine Machine;

  public RequestState() {
    BufferRead = new byte[BufferSize];
    RequestData = new StringBuilder(String.Empty);
    Request = null;
    ResponseStream = null;
  }
-------------------------------------------------------------------------------
  #region IDisposable
  private bool disposed = false;

  public void Dispose() {
    Dispose(true);
  }

  #region IDisposable
  private bool disposed = false;

  public void Dispose() {
    Dispose(true);
    // GC.SupressFinalize(this);         // What happens if I tell the GC that this object is alredy finalized??
  }

  protected virtual void Dispose(bool disposing) {
    if ( !this.disposed ) {
      if ( disposing ) {
        // Dispose managed resources.
        ResponseStream.Dispose();
        Machine = null;                 // Do I need this?
      }
      // release unmanaged ressources

      disposed = true;
    }
  }

  ~RequestState() {
    Dispose(false);
  }
  #endregion
}
#endregion
4

2 回答 2

3

如果他们不实现一次性模式,那么这些类的作者会说“这些东西不需要任何特殊清理”。

而且您也不需要分配null-GC的全部意义在于它会找到不再使用的东西-您不需要尝试“帮助它”(以及许多努力,如果它们对全部,实际上阻碍了GC)

你不应该调用GC.SupressFinalize()任何你不是类1的作者的对象。


1现在我正在等待评论指出我目前没有想到的一些极端情况。

于 2013-10-16T06:20:15.597 回答
1

您不需要显式设置对 的引用null,但这样做将允许这些实例被垃圾回收,即使您的实例在处理后继续被引用。

我个人的看法是,将引用设置null为不再需要该引用的时间是一种很好的做法,因为它有助于定位错误。

如果你实现了 Disposable 模式并且你的对象有一个终结器,你应该总是在你的方法中调用GC.SuppressFinalize()实例。Dispose这样做会通知运行时它不需要调用实例的终结器,因为该实例已被释放。

调用GC.SupressFinalize()不会导致垃圾收集器“错过”可能被收集的实例。

于 2013-10-16T06:28:41.300 回答