【问题标题】:Polymorphism in C++ why is this isn't working?C ++中的多态性为什么不起作用?
【发布时间】:2017-01-09 08:23:56
【问题描述】:
class Base {
    public:
    virtual void f();
    void f(int);
    virtual ~Base();
};

class Derived : public Base {
public:
    void f();
};

int main()
{
    Derived *ptr = new Derived;
    ptr->f(1);
    delete ptr;
    return 0;
}

ptr->f(1);显示以下错误:“函数调用中的参数过多”。

为什么这是不可能的?派生不是继承了基础的所有函数并且可以免费使用其中的任何一个吗? 我可以显式调用它,它会起作用,但为什么不允许这样做?

【问题讨论】:

  • f(int)derived 中没有重载,你期望什么?
  • 对于多态性,ptr 应该是一个指向 base 类的指针。
  • 但是 Derived 不应该继承 Base 函数吗?或者它不适用于指针?
  • 我想我现在明白了,派生类可以访问函数,只是不在 main 中吗?

标签: c++ polymorphism


【解决方案1】:

你所看到的叫做隐藏

当您覆盖Derived 类中的函数void f() 时,您隐藏 Base 类中f 函数的所有其他变体。

您可以使用using 关键字解决此问题:

class Derived : public Base {
public:
    using Base::f;  // Pull all `f` symbols from the base class into the scope of this class

    void f() override;  // Override the non-argument version
};

【讨论】:

    【解决方案2】:

    正如@Some Programming Dude 所说:这是因为隐藏。

    用相对简单的语言理解隐藏

    Inheritance 旨在将Baseclass 变量/函数带入Derived 类。

    但是,在 1 个条件下:“如果它在派生类中不可用”

    由于f() 已经在Derived 中可用,所以从编译器的角度来看Base 类是没有意义的。

    这就是为什么在调用此函数时需要澄清范围的确切原因

    void main()
        {
            Derived *ptr = new Derived;
            ptr->Base::f(1);
            delete ptr;
        }
    

    【讨论】:

      【解决方案3】:

      暂时假设Derived 确实可以访问函数void Base::f(int);。那么它将是function overloading 的情况。但是,这是 function overloading 的无效情况,因为一个函数 f(int); 在 Base 中,而另一个函数 f(); 在 Derived 中。 Function Overloading 发生在单个类中。 Function Overriding 跨类发生。您发布的示例是Name Hiding in Inheritance的案例

      【讨论】:

        【解决方案4】:

        “Derived *ptr” 这个定义将只允许“ptr”访问通过 Derived 类或其子类定义的所有成员函数。但是,它不允许你访问由于继承而进入 Derived 类的成员函数。

        如果您想访问函数“f”的基类版本,请使用“Base *ptr”,它会自动选择正确的函数版本,如图所示:)

        class Base {
            public:
                virtual void f()
                {
                    cout<<"Here 2"<<endl;
                }
                void f(int x)
                {
                    cout<<"Here 1"<<endl;
                }
                virtual    ~Base() {}
        };
        
        class Derived : public Base {
            public:
                void f()
                {
                    cout<<"Here 3"<<endl;
                }
                virtual   ~Derived() {}
        };
        
        int main()
        {
            Base *ptr = new Derived;
            ptr->f(1);
            delete ptr;
            return 0;
        }
        

        输出是 这里 1

        【讨论】:

          猜你喜欢
          • 1970-01-01
          • 2016-08-22
          • 2011-03-21
          • 1970-01-01
          • 1970-01-01
          • 2012-11-24
          • 2017-11-07
          • 1970-01-01
          • 1970-01-01
          相关资源
          最近更新 更多