假设我有一个Animal类Cow继承的基类,以及一个Barn包含Animal向量的类,让我们假设Animal类有一个虚函数scream(),它Cow会覆盖.
使用以下代码:
Animal.h
#ifndef _ANIMAL_H
#define _ANIMAL_H
#include <iostream>
using namespace std;
class Animal {
public:
Animal() {};
virtual void scream() {cout << "aaaAAAAAAAAAAGHHHHHHHHHH!!! ahhh..." << endl;}
};
#endif /* _ANIMAL_H */
Run Code Online (Sandbox Code Playgroud)
Cow.h
#ifndef _COW_H
#define _COW_H
#include "Animal.h"
class Cow: public Animal {
public:
Cow() {}
void scream() {cout << "MOOooooOOOOOOOO!!!" << endl;}
};
#endif /* _COW_H */
Run Code Online (Sandbox Code Playgroud)
Barn.h
#ifndef _BARN_H
#define _BARN_H
#include "Animal.h"
#include <vector>
class Barn {
std::vector<Animal> animals;
public:
Barn() {}
void insertAnimal(Animal animal) {animals.push_back(animal);}
void tortureAnimals() {
for(int a = 0; a < animals.size(); a++)
animals[a].scream();
}
};
#endif /* _BARN_H */
Run Code Online (Sandbox Code Playgroud)
最后是main.cpp
#include <stdlib.h>
#include "Barn.h"
#include "Cow.h"
#include "Chicken.h"
/*
*
*/
int main(int argc, char** argv) {
Barn barn;
barn.insertAnimal(Cow());
barn.tortureAnimals();
return (EXIT_SUCCESS);
}
Run Code Online (Sandbox Code Playgroud)
我得到这个输出:
aaaAAAAAAAAAAGHHHHHHHHHH!!! ahhh...
Run Code Online (Sandbox Code Playgroud)
我应该如何编写此获得MOOooooOOOOOOOO!!!(和任何其他类继承Animal想scream()成为)呢?
fre*_*low 12
A std::vector<Animal>只能包含Animal对象,而不能包含Cow对象.
这是当你说barn.insertAnimal(Cow());:
Cow().animal由于您选择按值传递,因此该参数是从该临时母牛复制构造的.这animal是Animal临时牛的部分副本.这称为对象切片.animal.现在你已经有了一头牛和两只额外的动物,但你只想要一头牛!animal因为insertBarn返回而被销毁.这是什么教训?不要按价值传递动物,也不要按价值存放动物.运行时多态性需要一个间接级别.你可能想要一个std::vector<Animal*>或std::vector<shared_ptr<Animal> >或boost::ptr_vector<Animal>.