2013-10-16 25 views
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 
+0

可能的重複:http://stackoverflow.com/questions/538060/proper-use-of-the-idisposable-interface – Steve

+0

@Steve,謝謝我正在尋找這樣的文章。這爲我在.NET中對清潔資源的混淆帶來了更多的光明 – Marschal

回答

3

如果他們不執行一次性圖案,然後這些類的作者們說:「這些事情並不需要任何特殊的清洗向上」。

而且你也不需要指定null - GC的全部重點是它發現不再使用的東西 - 你不需要試圖「幫助它」(並且很多努力,如果他們完全沒有任何影響,實際上阻礙了GC)

你不應該在任何物體上呼叫GC.SupressFinalize()你不是它的類的作者。


而現在我在等待一個指向了一些邊緣的情況下,我目前還沒有考慮到的註釋。

1

您不需要明確設置對null的引用,但是這樣做將允許這些實例被垃圾收集,即使您的實例在處置後仍然被引用。

我的個人意見是,當該引用不再需要時,將參考設置爲null是一種很好的做法,因爲它有助於查找錯誤。

如果您實施一次性模式並且您的對象具有終結器,則應始終在您的Dispose方法內的實例上調用GC.SuppressFinalize()。這樣做會通知運行時,它不需要調用實例的終結器,因爲實例已經被處置。

調用GC.SupressFinalize()不會導致垃圾收集器「錯過」可能收集的實例。