我有四个不同的 C++ 类;
Comp()
,其中包含 Parent()
,后者有两个子元素 ChildA()
和 ChildB()
。我想根据某些参数在 ChildA
内部动态创建 ChildB
或 Comp()
的实例。
我的代码看起来有点像这样:
class Parent {
public:
foo();
};
class ChildA : public Parent {
public:
foo(); // Overrides Parent.foo()
};
class ChildB : public Parent {
public:
foo(); // Overrides Parent.foo()
};
class Comp {
public:
Init(uint8_t someParam){
if(someParam){
obj = new ChildA();
}
else{
obj = new ChildB();
}
}
doFoo(){
obj->foo();
}
private:
Parent* obj;
};
但是,这不能编译。它向我抛出链接器错误,说我对
Parent::foo()
有未定义的引用
/build/libComp.a(Comp.cpp.o): In function `Comp::doFoo()':
Comp.cpp:(.text._ZN6Memory8readByteEt+0x4e): undefined reference to `Parent::foo()'
我觉得我在这里错过了一些基本的东西。我有 Python 编程背景,所以我还没有完全将我的思维过程转向 C++。我可以这样使用类吗?
作为一名 Python 程序员,您已经习惯了每个方法都是虚拟方法的世界,并且重载意味着您只需替换字典中的值。 C++ 有点不同。
所以第一个解决方案是定义
Parent::foo
方法。您已经声明了它,该类不是模板 - 所以您必须在某处定义主体。无论如何,这对你没有帮助,因为调用 obj->foo();
意味着调用 Parent::foo()
方法,我想这不是你想要的。
现在我们正在进入虚拟方法的世界:在 C++ 中,您必须显式地将方法声明为
virtual
:
class Parent {
public:
virtual foo();
};
您仍然需要在某处定义
Parent::foo()
的主体。
如果你不想通过设计来定义它,你可以将这个方法设为abstract(这样类
Parent
也变得抽象,并且不能创建该类的实例):
class Parent {
public:
virtual foo() = 0;
};
您不需要将派生类的方法
foo
声明为虚拟方法(无论如何它们都会是),但最佳实践是添加 override
或 final
说明符:
class ChildA : public Parent {
public:
foo() final; // Overrides Parent.foo()
};
class ChildB : public Parent {
public:
foo() override; // Overrides Parent.foo()
};
不同之处在于,您无法为
ClassA
重写此方法,但可以为 ClassB
执行此操作。