如何使用多态性从基类访问派生类向量成员? [英] How to use polymorphism to access derived class vector member from base class?

查看:21
本文介绍了如何使用多态性从基类访问派生类向量成员?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

It's said that with polymorphism, we can access a derived class member field with it's base class object like this:

#include <iostream>
#include <string>
#include <vector>

using namespace std;

class Tool{
    public:
        Tool(){}
        Tool(string name){
            this->name = name;
        }
        virtual string getInfo(){
            return name;
        }
    //protected:
        string name;
};

class Computer: public Tool{
    public:
        Computer(string name, int price){
            this->name = name;
            this->price = price;
        }
        virtual string getInfo(){
            return name + ": " + to_string(static_cast<long long>(price));
        }
    //protected:
        int price;
};

class Person{
    public:
        Person(){}
        Person(string name){
            this->name = name;
        }
        virtual string getInfo(){
            return name;
        }
        virtual void addTools(Computer cmp){
            tools.push_back(cmp);
        }
    //protected:
        vector<Tool> tools;
        string name;
};

class Programmer: public Person{
    public:
        Programmer(string name, string job){
            this->name = name;
            this->job = job;
        }
        string getInfo(){
            return name + ": " + job;
        }
    //protected:
        string job;
};

int main(){
    Person prs("Person");
    Programmer prg("Daphloon", "programmer");

    Person* prs1 = &prs;
    Person* prs2 = &prg;

    cout << prs1->getInfo() << endl;    // result: Person
    cout << prs2->getInfo() << endl;    // result: Daphoon: programmer

    Tool tl("Hammer");
    Computer cmp("PC", 100);

    Tool* tl1 = &tl;
    Tool* tl2 = &cmp;


    cout << tl1->getInfo() << endl;     // result: Hammer
    cout << tl2->getInfo() << endl;     // result: PC: 100

    prs2->addTools(cmp);

    cout << prs2->tools[0].getInfo() << endl;   // result: PC
                                                // I expect the result will be: PC: 100 

    return 0;
}

The result wasn't what I expected. What I need is every derived class from Person have a vector tools that contains object that inherit from Tool class. If it described with word, it will be, "This Person, a Programmer, has some tools. His first Tool is a Computer. If you want to know what's it's price, use getInfo()."

  1. Why vector take the base class instead of the derived class?
  2. Is there any data loss from cmp object when i put it inside tools vector?
  3. Is this happen because tools vector member take Tool as it's type?

解决方案

Runtime polymorphism in C++, achieved via virtual functions, works on covariant types. The only covariant types are pointers and references. Since you have a vector<Tool>, you lose polymorphism. To retain it, store a vector<Tool*>. Even better, store a vector<unique_ptr<Tool>>.

Assigning a derived class object to a base class is called object slicing. You do lose information contained in the derived object. This is the case when you are inserting a Computer into a vector<Tool>.

这篇关于如何使用多态性从基类访问派生类向量成员?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆