throwing exceptions out of a destructor

后端 未结 16 1867
暗喜
暗喜 2020-11-22 00:23

Most people say never throw an exception out of a destructor - doing so results in undefined behavior. Stroustrup makes the point that \"the vector destructor e

16条回答
  •  栀梦
    栀梦 (楼主)
    2020-11-22 00:56

    Its dangerous, but it also doesn't make sense from a readability/code understandability standpoint.

    What you have to ask is in this situation

    int foo()
    {
       Object o;
       // As foo exits, o's destructor is called
    }
    

    What should catch the exception? Should the caller of foo? Or should foo handle it? Why should the caller of foo care about some object internal to foo? There might be a way the language defines this to make sense, but its going to be unreadable and difficult to understand.

    More importantly, where does the memory for Object go? Where does the memory the object owned go? Is it still allocated (ostensibly because the destructor failed)? Consider also the object was in stack space, so its obviously gone regardless.

    Then consider this case

    class Object
    { 
       Object2 obj2;
       Object3* obj3;
       virtual ~Object()
       {
           // What should happen when this fails? How would I actually destroy this?
           delete obj3;
    
           // obj 2 fails to destruct when it goes out of scope, now what!?!?
           // should the exception propogate? 
       } 
    };
    

    When the delete of obj3 fails, how do I actually delete in a way that is guaranteed to not fail? Its my memory dammit!

    Now consider in the first code snippet Object goes away automatically because its on the stack while Object3 is on the heap. Since the pointer to Object3 is gone, you're kind of SOL. You have a memory leak.

    Now one safe way to do things is the following

    class Socket
    {
        virtual ~Socket()
        {
          try 
          {
               Close();
          }
          catch (...) 
          {
              // Why did close fail? make sure it *really* does close here
          }
        } 
    
    };
    

    Also see this FAQ

提交回复
热议问题