如果我有一个 C++ 函数/方法,例如:
getSound(Animal a){
a.printSound();
}
然后传递给它一个Dog扩展类Animal但覆盖动物方法的对象,有没有办法在里面printSound()使用狗?printSound()getSound()
我已经尝试printSound()在Animal类定义中进行虚拟化,但我仍然得到原始printSound().
提前致谢。
如果我有一个 C++ 函数/方法,例如:
getSound(Animal a){
a.printSound();
}
然后传递给它一个Dog扩展类Animal但覆盖动物方法的对象,有没有办法在里面printSound()使用狗?printSound()getSound()
我已经尝试printSound()在Animal类定义中进行虚拟化,但我仍然得到原始printSound().
提前致谢。
这是因为object-slicing,因为您按值接受参数。
通过引用接受它:
void getSound(Animal & a); //now reference
如果Animal::printSound()不改变对象的状态,则使其成为const成员函数(如果它不是 const 已经),然后通过const引用接受参数:
void getSound(Animal const & a); //now const reference
虚拟printSound化是正确的。将 的签名更改getSound为Animal&或const Animal&。通过取值,您正在从您Animal的 构建一个新的,而这只是一个,而不是一个。AnimalDogAnimalDog
当您调用时getSound,您正在传递Animal按值。这意味着Dog通过调用Animal的复制构造函数来制作 的副本。的Animal复制构造函数构造一个Animal,而不是一个Dog。您可能希望通过引用传递:
getSound(Animal& a){
a.printSound();
}
你基本上做对了所有事情,除了一件事。
通过引用传递 Animal 对象
getSound(Animal &a);
或者提供指向相关对象的指针。
getSound(Animal *a) {
a->printSound(); //Mind the -> in this case.
}
要调用这个函数,你可以这样:
Dog D;
getSound(&D); //Passes a pointer to the function.
否则,您将构造一个“动物”类型的新对象,而不是真正“传递”一只狗。
实际上,最好使用指针解决方案,否则在传递派生对象时会遇到问题,因为它需要一个类型的对象Animal并且不会满足于其他任何东西。