在c++中,继承关系有:单继承和多重继承;在多重继承中,有一种继承是菱形继承(钻石继承)关系比较复杂。如下:
情形1:类B,C继承A,类D继承B,C
class A
{
public:
int base;
};
class B :public A {
public:
int b;
};
class C :public A {
public:
int c;
};
class D :public B, public C
{
public:
int d;
};
void main(){
A a;
B b;
C c;
D d;
std::cout << "Base::base=" << a.base << std::endl;
std::cout << "b::base=" << b.base << std::endl;
std::cout << "c::base=" << c.base << std::endl;
std::cout << "d::base=" << d.base << std::endl; //编译无法通过,需要指定B或者C的作用域
}
问题:类D同时继承了B,C,同时继承了基类A。基类成员base无法唯一确定,需要用B或者C的作用域限定。有没有办法让类D只继承一份base呢?虚继承
情形2:
class A
{
public:
int base;
};
class B :virtual public A {
public:
int b;
};
class C :virtual public A {
public:
int c;
};
class D :public B, public C
{
public:
int d;
};
void main(){
A a;
B b;
C c;
D d;
std::cout << "Base::base=" << a.base << std::endl;
std::cout << "b::base=" << b.base << std::endl;
std::cout << "c::base=" << c.base << std::endl;
std::cout << "d::base=" << d.base << std::endl; //正确,无要指定B或者C的作用域
}
通过查看内存,虚继承的子类有一个虚基类指针(4字节)。类D的对象虽然同时继承了B和C,但是虚基类指针地址一样。
因此,虚继承有效解决了菱形继承存在二义性问题。