将 BASE-DERIVED class 存储在同一个容器中

Store BASE-DERIVED class in same container

我的概念(不是真实的)class 层次结构为:

struct Pet{};
struct Cat : Pet{};
struct Dog : Pet{};

对象如下:

Pet p("unknown");
Cat c("Kitty");
Dog D("Tommy");

现在如何将对象 p,c,d 存储在像 std::vector 这样的单个容器中。但我想不出办法。当我将 std::vector<Pet> 其他 class 切片时。我什至无法将它们作为指针存储在容器中,因为指针仍然具有不同的类型。

通常将它们放在同一个容器中的唯一原因是将它们用作基本类型,利用多态性根本不关心具体类型是什么。这需要使用虚拟方法。例如:

struct Pet {
    virtual ~Pet();
    virtual void speak(std::ostream &) const = 0;
};

Pet::~Pet() {}

struct Cat : public Pet {
    virtual void speak(std::ostream &) const override;
};

void Cat::speak(std::ostream & o) const {
    o << "Meow!\n";
}

struct Dog : public Pet {
    virtual void speak(std::ostream &) const override;
};

void Dog::speak(std::ostream & o) const {
    o << "Woof!\n";
}

现在我们有了一个虚拟方法 (speak(std::ostream&)),我们可以通过指向 Pet 的指针调用它,而无需知道宠物的实际类型:

std::vector<std::unique_ptr<Pet>> pets;
pets.emplace_back(std::make_unique<Cat>());
pets.emplace_back(std::make_unique<Dog>());

for (auto const & pet : pets) {
    pet->speak(std::cout);
}

显示:

Meow!
Woof!

如果您不能像这样将容器中的所有对象都视为基本实例,那么就没有理由将它们放在同一个容器中 - 这有什么意义?