虚继承

C++ 中,多继承时很容易产生命名冲突,即使我们很小心地将所有类中的成员变量和成员函数都命名为不同的名字,命名冲突依然有可能发生,比如非常经典的菱形继承层次。

虚继承就是用来解决菱形继承问题的。

一般继承

class A { void print(); }; class B : public A { void print(); }; class C : public C { void print(); };

在这样一系列继承体系中,A 包含一份 print(),B 包含了两份,而 C 则包含了三分 print()。这里总共有 6 份独立的 print() 函数。虽然在 C 中调用 B::print() 感觉和 B 中调用 print() 效果一样,但他们确实是作为两个副本存在。

虚继承

class A { void print(); }; class B : virtual public A { void print(); }; class C : virtual public A { void print(); };

B只含有一份 print() 副本,但是却可以通过 A::print() 调用 A 的 print() 函数。同理,C 也只包含了一份 print() 副本。这里总共只有 3 份 print() 副本。

虚继承中基类的数据并没有变多一份给派生类,而只是使用权移交了,就好像 A 有一栋楼,虚继承给 B,名义上 B也拥有了这栋楼,可以使用,但是并没有真正为B另外建一栋一模一样的楼。