Will the destructor of the base class called if an object throws an exception in the constructor?

老子叫甜甜 提交于 2020-01-11 04:28:06

问题


Will the destructor of the base class be called if an object throws an exception in the constructor?


回答1:


If an exception is thrown during construction, all previously constructed sub-objects will be properly destroyed. The following program proves that the base is definitely destroyed:

struct Base
{
    ~Base()
    {
        std::cout << "destroying base\n";
    }
};

struct Derived : Base
{
    Derived()
    {
        std::cout << "throwing in derived constructor\n";
        throw "ooops...";
    }
};

int main()
{
    try
    {
        Derived x;
    }
    catch (...)
    {
        throw;
    }
}

output:

throwing in derived constructor
destroying base

(Note that the destructor of a native pointer does nothing, that's why we prefer RAII over raw pointers.)




回答2:


Yes. The rule is that every object whose constructor has finished successfully will be destructed upon exception. E.g:

class A {
public:
    ~A() {}
};

class B : public A {
public:
    B() { throw 0; }
    ~B() {}
};

~A() is called. ~B() is not called;

EDIT: moreover, suppose you have members:

struct A {
    A(bool t) { if(t) throw 0; }
    ~A() {}
};

struct B {
    A x, y, z;
    B() : x(false), y(true), z(false) {}
};

What happens is: x is constructed, y throws, x is destructed (but neither y nor z).




回答3:


When an exception is thrown, the destructors are called for all (sub-) objects whose constructors were successfully run. This extends to data members and base classes alike.

For example, for this code

struct base {};

struct good {};

struct bad {
  bad() {throw "frxgl!";}
};

struct test : public base {
  std::string s;
  good g;
  bad b;
  test() {}
};

before test's constructor is executed, first the constructor for the base class is called, then the constructors for s, g, and b. Only if these finish successfully, the constructor for test is executed. When the exception is thrown during the construction of b, the base class constructors as well as the constructors for the data members s and g have been fully executed, so their destructors are run. The constructor of test itself and of b have not been run successfully, so their destructors are not run.




回答4:


From Standard docs, 15.3 - 11,

The fully constructed base classes and members of an object shall be destroyed before entering the handler of a function try- block of a constructor or destructor for that object.



来源:https://stackoverflow.com/questions/3759270/will-the-destructor-of-the-base-class-called-if-an-object-throws-an-exception-in

标签
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!