hu *_*ang 1 c++ overload-resolution implicit-conversion
为什么以下重载函数调用不明确?编译错误:
调用重载'test(long int)'是模棱两可的,候选者是:void test(A)| 无效测试(B)|
代码:
class A
{
public:
A(int){}
A(){}
};
class B: public A
{
public:
B(long){}
B(){}
};
void test(A a)
{
}
void test(B b)
{
}
void main()
{
test(0L);
return;
}
Run Code Online (Sandbox Code Playgroud)
您遇到错误,因为重载决策必须从两个同样可行的函数中选择(两者都具有用户定义的转换).函数重载决策是一个非常复杂的主题.有关超载分辨率的更多详细信息,请参阅Stephan T. Lavavej 最近的演讲.通常最好创建单参数构造函数explicit,然后使用显式构造函数参数调用函数.
test(0L)与任何重载都不完全匹配,因为没有过载test(long).您提供的两个重载都在其参数上具有用户定义的转换,但编译器认为它们同样可行.所述A过载必须做一个标准转换(长为int),接着是用户定义的转换(INT到A),并且所述B过载一个用户定义的转换(长至B).但两者都是隐含的用户定义转换序列.
这些排名如何?标准在13.3.3.2中对隐式转换序列进行排序[over.ics.rank]
如果S1是S2的适当子序列,则标准转换序列S1是比标准转换序列S2更好的转换序列
这些类型的打破平局例如,如果A将是来自B的派生类(或反之亦然),则适用.但是这里转换序列都不是另一个的后续序列.因此它们同样可行,编译器无法解析调用.
class A
{
public:
explicit A(int){}
A(){}
};
class B: public A
{
public:
explicit B(long){}
B(){}
};
void test(A a)
{}
void test(B b)
{}
int main()
{
test(A(0L)); // call first overload
test(B(0L)); // call second overload
return 0;
}
Run Code Online (Sandbox Code Playgroud)
注意:int main()不是void main().
| 归档时间: |
|
| 查看次数: |
808 次 |
| 最近记录: |