c++ - 类中未调用虚函数
问题描述
在下面的main()
函数中,d
是一个基类指针(类型A
),它指向派生类(类型B
)。然而,当f(int)
在这个指针上调用成员函数时,即d->f(1)
编译器调用基类A(标记为)中的非虚拟函数#2
,即
void f(int n) const { std::cout << n; }
为什么?我期待着,因为基类中还有一个虚函数A
virtual void f(int n) { std::cout << n; }
f(int)
派生类中的两个函数之一B
将被调用。我哪里错了?
class A
{
public:
A() {}
public:
virtual void f(int n) { std::cout << n; } // #1
virtual ~A() { }
void f(int n) const { std::cout << n; } // #2 this function is called when d->f(1) is executed in main()
};
class B
: public A
{
public:
void f(int n) { std::cout << n; } // #3
void f(int n) const { std::cout << n; } // #4
};
int main()
{
B b;
const A* d = &b;
d->f(1); // this calls function #2 above - why?
std::cout << std::endl;
return 0;
}
解决方案
d
是一个指向 const 的指针A
。这意味着对成员函数的任何调用都将调用 const 限定的重载(如果存在)。f
在您的情况下,基类 ( ) 中的 const 限定版本#2
is not virtual
,因此d
指向B
对象的事实并不重要。基类 const 限定的重载是被选择调用的重载。
如果您f
在基类中virtual
进行了 const 限定的重载,则将选择派生类 ( #4
) 中的 const 限定的重载。
类似地,如果d
是指向非 const 的指针,则将调用派生类 ( ) 中A
的非 const 限定重载,因为基类 ( ) 中的重载是。f
#3
#1
virtual
推荐阅读
- javascript - 在替换之前删除属性会改变垃圾收集优先级吗?
- swift - 范围的多个循环?在一定范围内?
- php - 将 post 方法数据传递到导航栏而不标签
- r - 使用 Crosstable() 显示缺失值
- c++ - 为什么没有 std::vector
有转换运算符 std::span ? - java - 如何修复 - 如果没有 @Inject 构造函数或 @Provides-annotated 方法,则无法提供
- ios - 使用 soto-cognito-authentication-kit
- selenium - 使用 Selenium 的 ElementNotInteractableException
- python - 使用 Weka 在 Jupyter Notebook 中进行预测
- c - 增加 C 字符串中的空字符和 C 字符串索引中的 strlen() 用法