c# - Utilisation appropriée de l'interface IDisposable

Mots clés : c#.netgarbage-collectionidisposablec#

meilleur 5 Réponses c# - Utilisation appropriée de l'interface IDisposable

vote vote

100

public void Cleanup() 
public void Shutdown() 
public void Dispose() 
public interface IDisposable {    void Dispose() } 
public void Dispose() {    Win32.DestroyHandle(this.CursorFileBitmapIconServiceHandle); } 
public void Dispose() {    //Free unmanaged resources    Win32.DestroyHandle(this.CursorFileBitmapIconServiceHandle);     //Free managed resources too    if (this.databaseConnection != null)    {       this.databaseConnection.Dispose();       this.databaseConnection = null;    }    if (this.frameBufferImage != null)    {       this.frameBufferImage.Dispose();       this.frameBufferImage = null;    } } 
~MyObject() {     //we're being finalized (i.e. destroyed), call Dispose in case the user forgot to     Dispose(); //<--Warning: subtle bug! Keep reading! } 
public void Dispose() {    //Free unmanaged resources    Win32.DestroyHandle(this.gdiCursorBitmapStreamFileHandle);     //Free managed resources too    if (this.databaseConnection != null)    {       this.databaseConnection.Dispose(); //<-- crash, GC already destroyed it       this.databaseConnection = null;    }    if (this.frameBufferImage != null)    {       this.frameBufferImage.Dispose(); //<-- crash, GC already destroyed it       this.frameBufferImage = null;    } } 
protected void Dispose(Boolean disposing) 
protected void Dispose(Boolean itIsSafeToAlsoFreeManagedObjects) {    //Free unmanaged resources    Win32.DestroyHandle(this.CursorFileBitmapIconServiceHandle);     //Free managed resources too, but only if I'm being called from Dispose    //(If I'm being called from Finalize then the objects might not exist    //anymore    if (itIsSafeToAlsoFreeManagedObjects)      {           if (this.databaseConnection != null)       {          this.databaseConnection.Dispose();          this.databaseConnection = null;       }       if (this.frameBufferImage != null)       {          this.frameBufferImage.Dispose();          this.frameBufferImage = null;       }    } } 
public void Dispose() {    Dispose(true); //I am calling you from Dispose, it's safe } 
~MyObject() {    Dispose(false); //I am *not* calling you from Dispose, it's *not* safe } 
public override void Dispose() {     try     {         Dispose(true); //true: safe to free managed resources     }     finally     {         base.Dispose();     } } 
protected void Dispose(Boolean iAmBeingCalledFromDisposeAndNotFinalize) {    //Free unmanaged resources    Win32.DestroyHandle(this.CursorFileBitmapIconServiceHandle); //<--double destroy     ... } 
public void Dispose() {    Dispose(true); //I am calling you from Dispose, it's safe    GC.SuppressFinalize(this); //Hey, GC: don't bother calling finalize later } 
~MyObject() {    //Free unmanaged resources    Win32.DestroyHandle(this.CursorFileBitmapIconServiceHandle);     //A C# destructor automatically calls the destructor of its base class. } 
vote vote

89

public class LoggingContext : IDisposable {     public Finicky(string name) {         Log.Write("Entering Log Context {0}", name);         Log.Indent();     }     public void Dispose() {         Log.Outdent();     }      public static void Main() {         Log.Write("Some initial stuff.");         try {             using(new LoggingContext()) {                 Log.Write("Some stuff inside the context.");                 throw new Exception();             }         } catch {             Log.Write("Man, that was a heavy exception caught from inside a child logging context!");         } finally {             Log.Write("Some final stuff.");         }     } } 
vote vote

77

public class SimpleCleanup : IDisposable {     // some fields that require cleanup     private SafeHandle handle;     private bool disposed = false; // to detect redundant calls      public SimpleCleanup()     {         this.handle = /*...*/;     }      protected virtual void Dispose(bool disposing)     {         if (!disposed)         {             if (disposing)             {                 // Dispose managed resources.                 if (handle != null)                 {                     handle.Dispose();                 }             }              // Dispose unmanaged managed resources.              disposed = true;         }     }      public void Dispose()     {         Dispose(true);         GC.SuppressFinalize(this);     } } 
vote vote

65

public static void Indented(this Log log, Action action) {     log.Indent();     try     {         action();     }     finally     {         log.Outdent();     } } 
Log.Write("Message at the top"); Log.Indented(() => {     Log.Write("And this is indented");      Log.Indented(() =>     {         Log.Write("This is even more indented");     }); }); Log.Write("Back at the outermost level again"); 
vote vote

53

class MyClass : IDisposable {     // ...      #region IDisposable Members and Helpers     private bool disposed = false;      public void Dispose() {         Dispose(true);         GC.SuppressFinalize(this);     }      private void Dispose(bool disposing) {         if (!this.disposed) {             if (disposing) {                 // cleanup code goes here             }             disposed = true;         }     }      ~MyClass() {         Dispose(false);     }     #endregion } 

Questions similaires