【问题标题】:Private non-virtual Base class function is called instead of the one in Derived class调用私有非虚拟基类函数而不是派生类中的函数
【发布时间】:2018-05-11 03:37:50
【问题描述】:
class Base{
public:
    void callF(){ F(); }
private:
    void F(){}
};
class Derived: public Base{
public:
    void F(){}
};
int main(){
    Derived d;
    d.callF();
}

令我惊讶的是,调用了 Base F()。我不明白为什么。 F() 在 Base 类中被声明并定义为私有,因此 Derived 对象甚至不知道 Base 中存在这样的函数。派生类有自己的 F(),但该函数被忽略。问题是“为什么要调用基类 F()?”。

【问题讨论】:

  • "我知道如果我在Base virtual中声明F(),问题就解决了,但是这个例子是怎么回事? - 你没有声明它virtual.
  • 主要问题是“为什么要调用 Base F()?”
  • @Grig ^^^^^^@Oliver 说了什么。
  • @user0042 你明白我的问题吗? “为什么要调用 Base F()?”
  • @Grig 因为您没有将派生类中的Base::F() 重写为virtual 函数。

标签: c++ inheritance private


【解决方案1】:

事情是这样的。

  1. Base::callF 函数被调用。它是公开的,因此在main 上调用它没有问题。
  2. Base::callF 函数想要调用名为 F 的函数。 Base::callF 唯一可见的 FBase::F。它是私有的,但 callFBase 的成员,因此它可以查看和使用所有其他成员,包括私有成员。
  3. Derived::F 函数与此无关。这只是另一个函数,与 Base::F 无关,恰好有一个相似的名称。

【讨论】:

    【解决方案2】:

    我不确定这是否能回答你的问题

    问题是“为什么要调用基类 F()?”。

    这是因为只有 virtual 函数可以在派生类中被覆盖(动态多态1),除非您使用 CRTP(静态多态1):

    template<class Derived>
    class Base{
    public:
        void callF(){ static_cast<Derived*>(this)->F(); }
    private:
        void F(){}
    };
    class Derived: public Base<Derived>{
    public:
        void F(){}
    };
    

    否则

        void callF(){ F(); }
    

    等价于

        void callF(){ Base::F(); }
    

    1)另见What is the difference between compile time polymorphism and static binding?

    【讨论】:

      猜你喜欢
      • 2019-01-09
      • 2015-04-16
      • 1970-01-01
      • 1970-01-01
      • 1970-01-01
      • 2016-10-08
      • 1970-01-01
      • 2021-05-09
      • 2020-09-30
      相关资源
      最近更新 更多