繁体   English   中英

基本类对象的c ++ std :: vector-派生类的运行方法

[英]c++ std::vector of base class objects -— running method of derived class

我想问一下Java中的“ instanceof”之类的东西。 我创建了一个简单的继承示例。 我的想法是做成一个Abstarct类Monster以及儿童Skeleton和Zombie子类,但是从抽象的角度来看它是行不通的,所以我们有std :: vectorBase类。 我将儿童对象推入向量。 我想调用子类的方法,但是被调用的方法是基类的空方法。 有现成的办法吗? 也许在c ++编程中,我们应该避免这种代码思考,而分别使用向量骨架和向量僵尸来做? 对不起我的英语不好。 希望你能理解我的问题。

 class Monster
        {
        public:
            virtual void describe() {};

        };

    class Skeleton : public Monster
        {
        public:
            Skeleton() {

            }
            ~Skeleton(){}
            void describe() override {
                std::cout << "I am skeleton" << std::endl;
            }
        };

    class Zombie : public Monster
        {
        public:
            Zombie(){}
            ~Zombie(){}
            void describe() override {
                std::cout << "I am Zombie" << std::endl;
            }
        };


        int main(void) {

            std::vector<Monster> potwory;
            potwory.push_back(Skeleton());
            potwory.push_back(Zombie());

            Skeleton sz;
            Zombie z;

            potwory.push_back(sz);
            potwory.push_back(z);

            for (auto i = 0; i < potwory.size(); i++) {
                std::cout << typeid(potwory[i]).name() << std::endl; // each of them is Monster object
                potwory[i].describe();  //here is calling method from base class , I want derived method.  
            }

            std::cin.get();
            return 0;

        }`

如前所述,由于仅将所有对象的Monster部分存储在向量中,因此遇到了切片问题。 您可以使用std::vector<Monster*>或自c ++ 11 std::vector<std::unique_ptr<Monster>> ,将指向Monster指针/ unique_ptr存储在向量中。 存储指向实际对象的指针可减轻切片的负担,因为该对象不是直接存储在向量中,而是仅是对堆上实际对象的引用,就像默认情况下使用Java一样。

如果您确实需要价值语义,则应该看看boost.polycollection,但这是一个相当高级的主题恕我直言。

感谢您的回答。 我无法为您添加帮助点,因为我是“ stack”的新手。 我读到这个问题,并写了一个解决方案。 如果有人需要这个。

#include <iostream>
#include <vector>
#include <memory>


class Monster
{
public:
    virtual void describe() {};
    virtual std::unique_ptr<Monster> copy_class()
    { 
        return std::unique_ptr<Monster>(std::make_unique<Monster>()); 
    }

};

class Skeleton : public Monster 
{
protected:
    const int life = 100;
public:
    Skeleton() {

    }
    ~Skeleton(){}
    void describe() override final {
        std::cout << "I am skeleton" << std::endl;
    }
    std::unique_ptr<Monster> copy_class() override 
    { 
        return std::unique_ptr<Monster>(std::make_unique<Skeleton>()); 
    }
};


class Zombie : public Monster
{
public:
    Zombie(){}
    ~Zombie(){}
    void describe() override {
        std::cout << "I am zombie" << std::endl;
    }
    std::unique_ptr<Monster> copy_class() override
    { 
        return std::unique_ptr<Monster>(std::make_unique<Zombie>());
    }
};


class UpgradeSkeleton final: public Skeleton
{
public:
    UpgradeSkeleton(){}
    ~UpgradeSkeleton() {}
    std::unique_ptr<Monster> copy_class() override { return std::unique_ptr<Monster>(std::make_unique<UpgradeSkeleton>()); }
};

int main(void) {

    std::vector<std::unique_ptr<Monster>> monsters;

    Skeleton s;
    Zombie z;
    UpgradeSkeleton us;

    monsters.push_back(std::unique_ptr<Monster>(s.copy_class()));
    monsters.push_back(std::unique_ptr<Monster>(z.copy_class()));
    monsters.push_back(std::unique_ptr<Monster>(us.copy_class()));



    for (auto &p : monsters) {
        p->describe();
    }

    std::cin.get();
    return 0;

}

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM