3
#include<iostream.h>  
class A{  
  public:  
        int i;  
            A(int j=3):i(j){}  
};  
class B:virtual public A{  
  public:  
        B(int j=2):A(j){}  
};  
class C:virtual public A{  
  public:  
        C(int j=1):A(j){}  
};  
class D:public B, public C {    
  public:  
        D(int j=0):A(j), B(j+1), C(j+2){}  
};

int main()  
{  
    D d;   
    cout<<d.i;  
    return 0;
}

I am not being able to understand how the final output is zero. Every time j is initialized in default way to some fixed value, how is the value initialized in the constructor of class D being passed to class A?

2 Answers2

2

The rule with virtual base inheritance is:

"The most derived class in a hierarchy must construct a virtual base"

In your case, from the most derived class D You explicitly called the constructor of A by passing an argument 0 So it sets the i to 0. As mentioned in rule virtual base class is constructed through most derived class only and the other constructor calls through intermediate hierarchy have no effect since it is only constructed once.

The order of calling is:

A(int)
B(int)
C(int)

Good Read:
Why virtual base class constructors called first?

Community
  • 1
  • 1
Alok Save
  • 202,538
  • 53
  • 430
  • 533
2

Since A is a virtual base class, it should be constructed only once, so it is not possible to create it with different constructor parameters, and the C++ compiler has to choose one way of creating a base class.

The obvious question is: which one is used?

And the rule is: the one specified in the most derived class that inherits A directly.

The initialization order is simple: first A (with the parameter value from D constructor initialization list), then B (it is D's first ancestor; and it uses the instance of A created before), then C (and it shares the same A instance), finally D (and it also shares the same A object as B and C).

Ellioh
  • 5,162
  • 2
  • 20
  • 33
  • but we see that in A the value of int j=3 is fixed so even though 0 is passed through D to A, wont this value be overwritten to 3 again and finally initializing i to 3. how come i is intiallised to 0 by j and not using j=3 as mentioned in the constructor of A.?? – Mragank Yadav Jan 06 '13 at 11:45
  • 3 is a default value. It is used as a parameter ONLY if some other is not passed. In your case 0 is passed explicitly, 3 is simply ignored. – Ellioh Jan 06 '13 at 16:29