为什么派生类必须重新定义重写的基类方法
why a derived class must redefine an overrided base class method
我不明白为什么我需要重新定义一个覆盖的基类方法。
这里,如果我在派生类中注释foo()方法,它不会编译。
谢谢你的解释。
class Base {
public:
void foo() {
}
};
class Derived: public Base {
public:
#define compile_ok
#ifdef compile_ok
// if this method is commented, it does not compile
void foo() {
Base::foo();
}
#endif
void foo(int i) {
}
void test() {
foo();
foo(1);
}
};
void testOverride() {
Derived d;
d.test();
}
您的foo
声明采用单个int
参数将隐藏Base
中命名为foo
的任何函数。您可以从Base
中添加一个隐藏的名称,如下所示:
class Derived: public Base {
public:
using Base::foo; // Pulls foo from Base
void foo(int i) {
}
void test() {
foo();
foo(1);
}
};
您的foo(int)
隐藏了基类名称。像这样修复:
class Derived: public Base {
public:
using Base::foo;
void foo(int i) {
}
void test() {
foo();
foo(1);
}
};
答案,正如其他人已经说过的那样,是派生类型中的foo
隐藏了基类型中的 foo
。扩展一下这意味着什么,问题是查找有一组规则,编译器必须应用这些规则,直到找到标识符。一旦它找到了这个名字,它就不会继续寻找更好的匹配,它会尝试使用它所看到的。
当在Derived::test
中输入foo()
时,编译器必须解析foo
,它可以是任何类型(类型,[member]变量,[member]函数…)。为此,它开始查找Derived::test
内部可用的内容,并且那里没有声明foo
。然后将搜索范围扩大到完整类型Derived
,并发现存在一个成员函数foo
。此时,它停止*。如果没有找到Derived::foo(int)
,它将继续扩展搜索到基,然后是命名空间,然后是其他命名空间…
*在这种特殊情况下,由于标识符解析为一个函数,因此ADL启动时会采取额外的步骤(或者更确切地说,如果有非基本类型的参数传递给函数,则会启动)。
相关文章:
- 如何创建一个CMake变量,除非显式重写,否则使用默认值
- 不允许在类定义之外重写
- 将一个小的 C 定义重写为"normal" C++函数
- 重写自定义数组类的运算符/开始/结束
- 在不提供定义的情况下重写函数有什么意义?
- 如何重写 AcDbEntity::transformBy 以在移动或缩放时获取自定义实体转换
- 在C++中重写类型定义
- 使用函数定义和原型重写代码
- winapi - 我应该重写 CButton 还是 CWnd 以创建自定义控件
- 在C++03中定义重写合法吗
- C++中的重定义与重写
- c++重写已定义的变量
- 你能重写基类中定义的私有函数吗
- 如何为c++自定义迭代器重写*i++
- 提振.重写main时未定义的符号
- 在编译时自定义/重写符号名
- 为什么派生类必须重新定义重写的基类方法
- 重写由另一个ext定义的方法
- 将定义重写为c++
- Clang重写器:为无效程序添加结构定义