这种奇怪的多态行为需要解释

时间:2016-10-08 07:46:20

标签: c++ polymorphism

我正在学习多态,并尝试了一些基本的东西。在下面的代码中,我在基类s = pd.read_csv(StringIO(the_data), sep='|', header=None, squeeze=True) left = s.str.split(',').str[:3].apply(pd.Series) left.columns = ['Company', 'Date', 'Volume'] right = s.str.split(',').str[3:].str.join(',') \ .str.replace(r'[\[\]\{\}\']', '') \ .str.replace(r'(:\s+\d+)L', r'\1') \ .str.split(',', expand=True) right.columns = ['Car{}'.format(i) for i in range(1, 5)] pd.concat([left, right], axis=1) 中有一个虚函数display()。我创建了两个派生类Animal,继承自Dog继承的AnimalTommyDog函数仅在以下代码中的一个派生类(display()类中重写)。

Tommy函数中,我通过基类指针指向派生对象。我认为以下代码片段会给我一个错误。

main()

但是,它最终调用ptr = &dog; ptr->display(); 的父类的display()(i,e。Dog)。出于好奇,我删除了Animal函数其他派生类并检查输出,但我得到相同的行为,总是最终调用父类的display()。我不知道为什么会发生这种情况。我想我在这里遗漏了一些东西。请发布。帮助

display()

输出结果为:

#include <iostream>

    using namespace std;

    class Animal
    {
        protected:
            string name;
        public:
            Animal(string nam):name(nam){}

            virtual void display()const {cout<<"Base class.\n";}

        };

    class Dog : public Animal
    {
        public:
        Dog(string nam):Animal(nam){}

        };

    class Tommy : public Dog
    {
        public:
        Tommy(string nam):Dog(nam){}

        void display()const{cout<<"i am  "<<name<<endl;}
        };

    int main()
    {
        Animal *ptr;
        Dog dog("trace");
        Tommy tom("tommy");

        ptr = &dog;
        ptr->display();

        ptr = &tom;
        ptr->display();


        return 0;
        }

2 个答案:

答案 0 :(得分:1)

  

但是,它最终调用了Dog(即动物)的父类的display()。

这是完全预期的行为,因为您没有覆盖派生类display中的虚函数Dog

为了使派生类具有特定行为,您必须实现非纯虚函数display。您已经在Tommy类中实现了该函数,但在Dog类中没有这样的实现。

答案 1 :(得分:1)

第一次显示值时,它是Dog类型。 Dog没有重新定义显示,它使用Animal中的一个,因为它继承了这个功能。

第二次显示值时,它是Tommy类型。汤米重新定义了显示功能,即“我是汤米”。它将显示此字符串,因为它重新定义了此虚函数。

这是因为Tommy是动物,因为Tommy继承了继承Animal的Dog。可以这样想:每个Tommy都是动物,但不是每个动物都是Tommy也不是狗。

Virtual是C ++中的关键字,这意味着可以在子类中重新定义函数。

编辑:只是澄清什么是纯虚函数和虚函数。纯虚函数声明函数NEEDS将在其子类中重新定义,或者它将不会编译(即,此函数的基类中没有实现)。虚函数表明它可以在他的子类中重新定义(它在基类中有一个实现)。在此示例中,display是一个虚函数,而不是纯函数。