开发者

c++ inheritance and constructors

class A {
public:
      A(int i): data(i) {cout << "A::A(" << i << ")" << endl;}
      A(const char* s): data(0) { cout << "A::A(" << s << ")"<< endl;}
      ~A() { cout << "A::~A()" << endl;}
private:
int data;
};

class B:public A {
public:
    B(const A& a): A(a){ std::cout << "B::B开发者_高级运维(const A& a)" << std::endl;}
     ~B() { std::cout << "B::~B()" << std::endl;}
};

int main() {
    B b0(0);
    B b1("abc");
return 0;
}

Pretty straightforward, can someone explain why the output is :

 A::A(0)
 B::B(const A& a)
 A::~A()
 A::A(abc)
 B::B(const A& a)
 A::~A()
 B::~B()
 A::~A()
 B::~B()
 A::~A()


B b0(0); - there's no such constructor for B, so the compiler is looking for some constructor, that can be called with just one cast (one implicit cast is allowed, 2 are not), so it finds B::B(const A& a), because A has a constructor with only one parameter, and this is A::A(int i). This means, that 0 can be casted to int, so temporary A object is created (and destroyed, after B is created). So, here's why we have


 A::A(0)
 B::B(const A& a)
 A::~A()

Then the next is called: B b1("abc");, so here comes:


 A::A(abc)
 B::B(const A& a)
 A::~A()

This is absolutely the same as with int, but here with char*.

Then, both objects are destructed, so their destructors are called in the opposite order, as their constructors are called, that's where


 B::~B()
 A::~A()
 B::~B()
 A::~A()

comes from.

It looks confising, because you haven't overloaded A::A( const A& a) and you don't see, that it is called 2 times, too.

Cheers (:


A small edit: not A::A(), but A::A( const A& a) - thanks to Nim.


You don't have a default constructor for B, so the compiler finds the best alternatives (i.e. construct A first with the matching inputs and then construct B from that.)

sequence would be:

  • construct temporary A with int
  • construct B with this A
  • destroy that A
  • (you don't have a copy constructor for A, else you'd see that thrown in there too!)
  • same for string
  • then sequence of base class/derived class destructors.


A temporary A object is constructed, then passed via a const reference to B's constructor, where it is copied using the copy ctor (which you haven't augmented with debug output, so you can't see it) into the B object.

Destruction takes place in reverse order of construction; the temporaries are destroyed when the constructor which they were passed to is finished.


It constructs a temporary A with the argument in the B constructor which it uses to initialise B::A (via the default copy constructor - hence no output for A::A(const A&)) The temporary A is destroyed after the call to B::B is complete.


 1.  A::A(0)          <- temporary A in B b0(0) line
 2.  B::B(const A& a) <- construct b0, no visible call to A as you did not provide A(A const &)
 3.  A::~A()          <- destroy temporary A created in line 1        
 4.  A::A(abc)        <- temporary A in B b1("abc") line
 5.  B::B(const A& a) <- construct b1, no visible call to A as you did not provide A(A const &)
 6.  A::~A()          <- destroy temporary A created in line 4
 7.  B::~B()          <- b1 ~B() destructor
 8.  A::~A()          <- b1 ~A() destructor
 9.  B::~B()          <- b0 ~B() destructor
 10. A::~A()          <- b0 ~A() destructor


I'll try:

 A::A(0)          // 1: construct an A using A(int) ctor in line 1 of main
 B::B(const A& a) // 2: construct a B passing the previously constructed A by const ref
 A::~A()          // 3: destruct the temporary A made in 1
 A::A(abc)        // 4:  construct an A using A(const char*) ctor in line 2 of main
 B::B(const A& a) // 5: construct a B passing the previously constructed A by const ref
 A::~A()          // 6: destruct the temporary A made in 4
                  // unwind the stack on exit of main
 B::~B()          // destruct B made in main line 2
 A::~A()          // destruct A inherited by B made in main line 2
 B::~B()          // destruct B made in main line 1
 A::~A()          // destruct A inherited by B made in main line 1
0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜