为何重载STL类函数后,错误参数类型仍会调用该重载函数?
问题原因分析
你的代码出现这种情况的核心原因是C++的名称隐藏规则:当派生类中定义了与基类同名的成员函数时,基类中所有同名的重载成员都会被隐藏,编译器不会再去基类中查找这些被隐藏的版本。
在你的代码里:
MyStack继承自std::stack<double>,基类std::stack有多个push的重载版本(包括接受double&&、const double&的模板版本)。- 但你在
MyStack中定义了void push(char),这个同名函数会直接隐藏基类所有的push重载。
当你调用stack.push(3.)时,编译器只会在MyStack的作用域中查找push,只找到push(char)这一个候选。此时编译器尝试把double类型的3.隐式转换为char(虽然会截断数值,但C++允许这种隐式转换),所以最终调用了push(char)版本。
解决方法
如果想保留继承+重载的方式,只需在MyStack的public区域添加using声明,把基类的push成员引入派生类的作用域,让编译器能同时看到基类和派生类的push重载:
#include <iostream> #include <stack> class MyStack : public std::stack<double> { public: using std::stack<double>::push; // 引入基类的所有push重载 void push(char) { std::cout << "Using char overload of push function.\n"; } }; int main() { MyStack stack{}; stack.push(3.); // 现在会调用基类的double版本 stack.push('a'); // 调用派生类的char版本 }
这样编译器在查找push时,会同时考虑基类的push(double&&)和派生类的push(char),3.作为double会优先匹配基类的版本,而char类型的参数会匹配你定义的重载。
内容的提问来源于stack exchange,提问作者Kyci
相关产品推荐
相关产品推荐

