Does the using statement dispose only the first variable it create?

后端 未结 6 811
猫巷女王i
猫巷女王i 2021-01-12 15:27

Let\'s say I have a disposable object MyDisposable whom take as a constructor parameter another disposable object.

using(MyDisposable myDisposab         


        
相关标签:
6条回答
  • 2021-01-12 15:53

    It doesn't "dispose" anything. It calls the Dispose method of the object used within it. Its your job to clean up anything else.. perhaps by calling dispose on the other object.

    0 讨论(0)
  • 2021-01-12 15:53

    C#’s using statement provides a syntactic shortcut for calling Dispose on objects that implement IDisposable, using a try/finally block. For example:

    using (FileStream fs = new FileStream ("myFile.txt", FileMode.Open))
    {
    // ... Write to the file ...
    }
    

    The compiler converts this to: FileStream fs = new FileStream ("myFile.txt", FileMode.Open);

    try
    {
    // ... Write to the file ...
    }
    finally
    {
    if (fs != null) ((IDisposable)fs).Dispose();
    }
    

    The finally block ensures that the Dispose method is called even when an exception is thrown,1 or the code exits the block early.

    So for using single block will only ensure that the single disposable object will be disposed. on the other hand you can use a nested using statements. like

    using (myDisposable d = new myDisposable())
    {
      using(Disposable2 d2 = new Disposable2())
      {
    // do something and dispose...
      }
    }
    

    and this will be converted as

    try
    {
      // work around for myDisposable  
    
        try
         {
          // work around for Disposable2 
         }
        finally
        {
        if (d2 != null) 
             ((IDisposable)d2 ).Dispose();
        }    
    }
    finally
    {
         if (d!= null)
              ((IDisposable)d).Dispose();
    }
    
    0 讨论(0)
  • 2021-01-12 15:53

    You only initialized one disposable variable in the using statement. The AnotherDisposable nested object is created through normal initialization, not by using. So only the myDisposable variable you created with the using statement will automatically be disposed by it.

    0 讨论(0)
  • 2021-01-12 15:58

    Why not nest them?

    using(var outer = new AnotherDisposable())
    {
       using(var inner = new MyDisposable(outer))
       {
          //whatever
       }
    
    }
    

    Now at least you can be sure they'll be disposed off correctly.

    0 讨论(0)
  • 2021-01-12 16:04

    In this case, it won't dispose the AnotherDisposable. There are two solutions to this.

    First, what you would normally do is the following:

    using (AnotherDisposable anotherDisposable = new AnotherDisposable())
    using (MyDisposable myDisposable= new MyDisposable(anotherDisposable))
    {
    }
    

    However, there is a different way to go. It's normal that when a class takes a disposable, it itself will take care of disposing the object it took. E.g. the StreamReader that wraps a Stream will dispose of the Stream it wraps. That means that the construct you choose would work. You can implement this same feature in MyDisposable and then the approach you took will be OK.

    0 讨论(0)
  • 2021-01-12 16:09

    using is an equivalent of

    MyDisposable myDisposable = new MyDisposable(new AnotherDisposable());
    try
    {
        //whatever
    }
    finally
    {
        if (myDisposable != null)
            myDisposable.Dispose();
    }
    

    Thus, if myDisposable does not call Dispose on AnotherDisposable, using won't call it either.

    0 讨论(0)
提交回复
热议问题