函数可以接受抽象基类作为参数吗?

时间:2021-03-27 21:22:02

Having gotten comfortable with the idea of basic classes and encapsulation, I've launched myself towards understanding polymorphism, but I can't quite figure out how to make it work. Many of the examples I've searched through come across as really, really forced (classes Foo and Bar are just too abstract for me to see the utility), but here's how I understand the basic concept: you write a base class, derive a whole bunch of other things from it that change what the base methods do (but not what they "are"), then you can write general functions to accept and process any of the derived classes because you've somewhat standardized their appearance. With that premise, I've tried to implement the basic Animal->cat/dog hierarchy like so:

我已经对基本类和封装的想法感到满意,我已经开始着手理解多态性,但我无法弄清楚如何使其工作。我搜索过的很多例子都是真的,非常强迫(类Foo和Bar对我来说太抽象了,看不到实用程序),但这就是我理解基本概念的方法:你编写一个基类,派生出一个从它改变基本方法所做的一切其他事情(但不是它们“是什么”),然后你可以编写通用函数来接受和处理任何派生类,因为你有点标准化它们的外观。在这个前提下,我试图实现基本的Animal-> cat / dog层次结构,如下所示:

class Animal {
  public:
    virtual void speak() = 0;
};

class Dog : public Animal {
  public:
    void speak() {cout << "Bark bark!" << endl;}
};

class Cat : public Animal {
  public:
    void speak() {cout << "Meow!" << endl;}
};

void speakTo(Animal animal) {
    animal.speak();
}

where speakTo can take can take a general kind of animal and make it, well, speak. But as I understand it, this doesn't work because I can't instantiate Animal (specifically in the function argument). I ask, then, do I understand the basic utility of polymorphism, and how can I really do what I've tried to do?

在哪里说话可以采取一般种类的动物,并使它,好吧,说话。但据我所知,这不起作用,因为我无法实例化Animal(特别是在函数参数中)。我问,那么,我是否了解多态性的基本效用,我怎样才能真正做到我试图做的事情?

2 个解决方案

#1


17  

You cannot pass an Animal object to the derived class function because you cannot create an object of Animal class et all, it is an Abstract class.
If an class contains atleast one pure virtual function(speak()) then the class becomes an Abstract class and you cannot create any objects of it. However, You can create pointers or references and pass them to it. You can pass an Animal pointer or reference to the method.

您不能将Animal对象传递给派生类函数,因为您无法创建Animal类的对象等等,它是一个Abstract类。如果一个类包含至少一个纯虚函数(speak()),那么该类将成为一个抽象类,您无法创建它的任何对象。但是,您可以创建指针或引用并将它们传递给它。您可以传递Animal指针或方法的引用。

void speakTo(Animal* animal) 
{
    animal->speak();
}

int main()
{
    Animal *ptr = new Dog();
    speakTo(ptr);

    delete ptr;   //Don't Forget to do this whenever you use new()
    return 0;
}

#2


10  

You will need to pass a reference instead of a copy:

您需要传递引用而不是副本:

void speakTo(Animal& animal) {
    animal.speak();
}

#1


17  

You cannot pass an Animal object to the derived class function because you cannot create an object of Animal class et all, it is an Abstract class.
If an class contains atleast one pure virtual function(speak()) then the class becomes an Abstract class and you cannot create any objects of it. However, You can create pointers or references and pass them to it. You can pass an Animal pointer or reference to the method.

您不能将Animal对象传递给派生类函数,因为您无法创建Animal类的对象等等,它是一个Abstract类。如果一个类包含至少一个纯虚函数(speak()),那么该类将成为一个抽象类,您无法创建它的任何对象。但是,您可以创建指针或引用并将它们传递给它。您可以传递Animal指针或方法的引用。

void speakTo(Animal* animal) 
{
    animal->speak();
}

int main()
{
    Animal *ptr = new Dog();
    speakTo(ptr);

    delete ptr;   //Don't Forget to do this whenever you use new()
    return 0;
}

#2


10  

You will need to pass a reference instead of a copy:

您需要传递引用而不是副本:

void speakTo(Animal& animal) {
    animal.speak();
}