派生类与多继承的继承问题:让bar调用A_Derived的foo方法
解决菱形继承下的虚函数调用问题
你的代码核心问题是菱形继承导致的多实例冲突,加上对象切片丢失了派生类信息,使得调用bar()时无法触发A_Derived的foo()。以下是符合要求的修改方案:
问题根源
- 现有继承结构中,
B_Base和A_Derived分别独立继承A_Base,导致B_Derived对象内部存在两个完全独立的A_Base子对象,B_Base的bar()只会调用自身关联的那个A_Base的foo()。 main里的B_base var = B_Derived();是对象切片操作:var只是一个纯粹的B_base对象,B_Derived中A_Derived的部分被丢弃,自然无法访问其foo()。
修改方案
1. 用虚继承消除重复的基类实例
让B_Base和A_Derived都虚继承自A_Base,这样整个继承体系中只会存在一个A_Base实例,确保A_Derived的foo()能覆盖这个唯一基类的虚函数。
2. 避免对象切片,使用指针或引用
不能直接用B_base对象存储B_Derived实例,改用指针或引用,保留多态特性。
修改后的完整代码
#include <iostream> using namespace std; class A_Base { public: virtual void foo() { cout << "A_Base::foo()" << endl; } }; class A_Derived : virtual public A_Base { // 虚继承 public: void foo() override { cout << "A_Derived::foo()" << endl; } }; class B_Base : virtual public A_Base { // 虚继承 public: void bar() { foo(); } // 此时调用的是唯一A_Base实例的虚函数,会动态绑定到覆盖版本 }; class B_Derived : public B_Base, public A_Derived { }; int main () { // 用指针避免切片,确保多态生效 B_Base* var = new B_Derived(); var->bar(); // 现在会调用A_Derived::foo() delete var; return 0; }
关键说明
- 虚继承保证了
A_Base在整个继承树中只有一个实例,A_Derived的foo()会正确覆盖这个实例的虚函数。 - 使用
B_Base*指针指向B_Derived对象,避免了切片,调用bar()时,foo()会通过虚函数表动态绑定到A_Derived的实现。
内容的提问来源于stack exchange,提问作者tony_merguez
相关产品推荐
相关产品推荐

