我可以在基类中重载纯虚方法吗?

use*_*761 5 c++ inheritance interface

在下面的例子中,我有一个带有纯虚方法(又名FUN1)和普通方法(又名FUN2)的抽象类.

#include <iostream>

class A
{
public:
        virtual void fun(int i) = 0; // FUN1
        void fun() { this->fun(123); } // FUN2
};

class B : public A
{
public:
        virtual void fun(int i) { std::cerr << i << std::endl; }
};

int main(int,char**)
{
        B b;
        b.fun();
}
Run Code Online (Sandbox Code Playgroud)

为什么我不能在派生类上调用FUN2?g ++给出错误:

main.cpp:19:8:错误:没有匹配函数来调用'B :: fun()'


编辑:请注意,纯虚函数的重载问题是不同的.我不想覆盖方法.

Ant*_*vin 7

这是派生类成员查找的工作原理:在表达式中b.fun(),fun首先在范围内class B查找,查找查找B::fun(int).所以它停止,永远不会发现A::fun().

该标准的相关部分是10.2 [class.member.lookup]/4:

如果C包含名称的声明f,该声明集包含的每一个声明f宣布 C满足在其中查找出现的语言结构的要求.(...)如果生成的声明集不为空,则子对象集包含C自身,并且计算完成.

要使基类函数可以直接访问,可以using在派生类中使用声明,即using A::fun;.

对于在基类中实现的方法,替代方案有时有资格调用,即b.A::fun().


Ada*_*amF 5

尝试using A::fun;在B类中添加语句:

#include <iostream>

class A
{
public:
    virtual void fun(int i) = 0; // FUN1
    void fun() { this->fun(123); } // FUN2
};

class B : public A
{
public:
    using A::fun;
    virtual void fun(int i) { std::cerr << i << std::endl; }
};

int main(int, char**)
{
    B b;
    b.fun();
    b.fun(5);
}
Run Code Online (Sandbox Code Playgroud)

  • 请注意,`virtual`在这里是一个红鲱鱼.在B中定义一些函数`foo`会隐藏基类中的函数`foo`,除非你明确地导入它们. (2认同)