Is IDisposable.Dispose () appelé automatiquement? [dupliquer]

possible Duplicate:

le Éboueur va-t-il appeler IDisposable?Jetez-il pour moi?

j'ai une classe qui a des ressources non gérées. Ma classe implémente l' IDisposable interface et libère les ressources non managées dans le Dispose() la méthode. Dois-je appeler le Dispose() méthode sera appelée automatiquement en quelque sorte? Sera la Le Garbage Collector de l'appeler?

41
demandé sur Community 2011-08-06 17:29:21

4 réponses

Dispose() ne sera pas appelé automatiquement. S'il y a un finalizer il sera appelé automatiquement. La mise en œuvre de IDisposable fournit un moyen pour les utilisateurs de votre classe de libérer les ressources tôt, au lieu d'attendre le collecteur d'ordures.

la meilleure façon pour un client est d'utiliser l'instruction using qui traite l'appel automatique de Dispose() même s'il y a des exceptions.

A la mise en œuvre correcte de IDisposable est:

class MyClass : IDisposable
{
  private bool disposed = false;

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

  protected virtual void Dispose(bool disposing)
  {
    if(!disposed)
    {
      if(disposing)
      {
        // Manual release of managed resources.
      }
      // Release unmanaged resources.
      disposed = true;
    }
  }

  ~MyClass() { Dispose(false); }
}

Si l'utilisateur de la classe appelle Dispose() le nettoyage s'effectue directement. Si l'objet est rangé par le ramasseur d'ordures, il appelle Dispose(false) pour faire le nettoyage. Veuillez noter que les références gérées par finalizer (la méthode ~MyClass ) peuvent être invalides, de sorte que seules les ressources non gérées peuvent être libérées.

51
répondu Anders Abel 2015-03-12 12:08:46

pour vous assurer que les ressources sont correctement réparties, vous devez à la fois implémenter IDisposable et appeler Dispose dans le destructeur(finalizer).

class Foo : IDisposable
{
    private bool m_disposed = false;

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

    ~Foo()
    {
        Dispose(false);
    }

    protected void Dispose(bool disposing)
    {
        if (!m_disposed)
        {
            if (disposing)
            { 
                //release managed resources
            }
            //release unmanaged resources

            m_disposed = true;
        }
    }
}
6
répondu Danny Chen 2011-08-06 13:40:55

si vous instanciez votre objet dans une instruction using , Dispose () est appelé pour vous lorsque le code sort du using bloc

using(var myObject = new MyDisposableObject())
{
  blah();
} // Dispose() is called here (or whenever the code exits the block)

si vous n'utilisez pas using , c'est à vous (le code d'appel) de vous débarrasser de votre objet en vous débarrassant explicitement de L'appel().

de plus, vous (l'exécuteur de MyObject) pouvez ajouter le support pour un finaliseur au cas où votre interlocuteur n'appellerait pas Dispose(). Plus d'infos ici .

5
répondu Serge Wautier 2011-08-06 13:35:05

vous will doit appeler cette méthode manuellement, peut-être dans une construction comme

using(var myclass = new MyClass())
{
   // do something with myclass
}

// now 'myclass'is Disposed
4
répondu Hans Kesting 2011-09-16 13:36:54