基类的私有虚函数被派生的私有虚函数隐藏

Private virtual function of base is hidden by private virtual function of derived

以下代码

class A
{
public:
    void g(int x)
    {
        f(x);
    }

protected:
    virtual void f(int) = 0;
};

class B: public A
{
protected:
    virtual void f(float) = 0;

private:
    void f(int x) override final
    {
        f(float(x));
    }
};

class C: public B
{
private:
    void f(float) override final {}
};

int
main()
{
    C c;
    c.g(1);

    return 0;
}

使用 g++ -Woverloaded-virtual 编译会产生上述警告:

x.cc:19:7: warning: ‘virtual void B::f(int)’ was hidden [-Woverloaded-virtual]
  void f(int x) override final
       ^
x.cc:28:7: warning:   by ‘virtual void C::f(float)’ [-Woverloaded-virtual]
  void f(float) override final {}
       ^

我不明白这里隐藏了什么。从 C 的范围来看,只有一种可能重载到 f,因为 B::f(int)C.

中是私有的

B 的范围来看,有两个,但都在 B 中明确命名。

引用GCC manual

-Woverloaded-virtual (C++ and Objective-C++ only) Warn when a function declaration hides virtual functions from a base class. For example, in:

struct A {
    virtual void f();
};

struct B: public A {
    void f(int);
};

the A class version of f is hidden in B, and code like:

B* b;
b->f();

fails to compile.

警告告诉您函数 C::f(float) 隐藏了 B::f(int),那是因为 it does。访问说明符不影响重载,因此 B::f(int) 是私有的这一事实并不重要。即使 B::f(int) 是 public,它也不会被考虑用于重载决议,这就是 "hiding" 所指的。

I do not understand what is being hidden here. From the scope of C there is only one possible overload to f as B::f(int) is private within C.

名称查找和解析发生在应用访问规则之前。

当从 C 对象中查找名称 f 时,

B::f(int)C::f(float) 隐藏。这就是编译器警告您的内容。