C++ 派生类的虚函数调用基类的虚函数 #包括 使用名称空间std; 类小部件{ 公众: 整数宽度; 虚拟空间调整大小(){width=10;} }; 类SpeWidget:publicwidget{ 公众: 内部高度; void resize()覆盖{ //Widget::resize(); Widget*th=静态_转换(此); th->resize(); 高度=11; } }; int main(){ //Widget*w=新的Widget; //w->resize(); //std::cout width resize(); std::cout height
注释掉的代码是正确的C++ 派生类的虚函数调用基类的虚函数 #包括 使用名称空间std; 类小部件{ 公众: 整数宽度; 虚拟空间调整大小(){width=10;} }; 类SpeWidget:publicwidget{ 公众: 内部高度; void resize()覆盖{ //Widget::resize(); Widget*th=静态_转换(此); th->resize(); 高度=11; } }; int main(){ //Widget*w=新的Widget; //w->resize(); //std::cout width resize(); std::cout height,c++,virtual-functions,C++,Virtual Functions,注释掉的代码是正确的 #include <iostream> using namespace std; class Widget { public: int width; virtual void resize() { width = 10; } }; class SpeWidget :public Widget { public: int height; void resize() override { //Widget::resiz
#include <iostream>
using namespace std;
class Widget {
public:
int width;
virtual void resize() { width = 10; }
};
class SpeWidget :public Widget {
public:
int height;
void resize() override {
//Widget::resize();
Widget* th = static_cast<Widget*>(this);
th->resize();
height = 11;
}
};
int main() {
//Widget* w = new Widget;
//w->resize();
//std::cout << w->width << std::endl;
SpeWidget* s = new SpeWidget;
s->resize();
std::cout << s->height << "," << s->width << std::endl;
std::cin.get();
}
您的替代代码是错误的
Widget::resize();
Widget*th=static\u cast(此);
th->resize();
想想看:您是通过指向基类的指针调用一个虚拟函数的。当您对任何虚拟函数执行此操作时会发生什么?它调用的是最派生的版本。换句话说,是无休止的递归。请参阅:。因为
resize
是虚拟的
,即使您通过小部件调用它*
它将从派生类SpeWidget
调用“correct”函数。从超类调用该方法的正确语法是Widget::resize()
。也就是说,您只需编写void resize()覆盖{Widget::resize();height=11;}
,或者void resize()覆盖{this->Widget::resize();height=11;}
,如果你想的话。这个->小部件::resize()
很清楚地解释了这一点,我认为这是有道理的。我认为另一个解释是th
是静态播放之后的这个的副本。然后th->resize()
无法更改此
的内容。如果这有助于您思考,那就太好了。请记住:通过指针调用虚拟函数总是通过vtable,这意味着它总是调用最派生的版本。无法避免。但是直接调用命名版本(即“Widget::resize()”)强制调用特定版本(基类版本)。
Widget* th = static_cast<Widget*>(this);
th->resize();