[英]Why is it illegal for non-templated functions to have same name and arguments but different return types? (but legal for template functions?)
[英]Why no ambiguity when choosing between templated and non-templated functions with same signatures?
以下代码传递断言:
int foo() { return 1; }
template<typename T>
int foo() { return 2; }
int main() {
assert( 1 == foo() );
assert( 2 == foo<int>() );
return 0;
}
但是据我了解,根据C ++ 11标准的13.3.3 / 1段:
[...]给定这些定义,如果对于所有自变量
i
,ICSi(F1)
转换顺序都不比ICSi(F2)
差,则一个可行函数F1
被定义为比另一个可行函数F2
更好的函数,然后[ ...]F1
是非模板函数,F2
是函数模板专门化[...]
不应该这样,因为签名最终是相同的。 那么为什么在调用foo<int>()
时没有歧义呢? 我想念什么?
您引用的文本比较密集; 您必须仔细阅读。 “如果对于所有自变量i
,ICSi(F1)的转换顺序都不比ICSi(F2) 差 ,则F1优于F2” –在这里是对的,因为两个转换顺序相同,因此,两个转换顺序都不比F2 差。其他。 因此,现在转到最后一部分:“ 然后 F1是非模板函数,而F2是函数模板特化”。 没错,因此F1比F2更好。 规则分别用foo()
和foo<int>()
代替F1和F2,该规则表示foo()
比foo<int>()
更好。
糟糕,我回答了错误的问题。 正如评论所指出的那样,问题是,为什么显式调用foo<int>()
无法解析为foo()
? 答案是foo<int>()
是对显式模板实例化的调用,而不是对重载函数的调用。 考虑:
template <class Ty>
void f(Ty) { }
void f(int);
void g(int);
f(3.14); // calls f<double> (overloaded function call)
f(1); // calls f(int) (overloaded function call)
f<int>(3.14); // calls f<int> (explicit call of template instantiation)
g(3.14); // calls g(int)
在此示例中, f<int>
是模板专门化的名称。 它不是名为f
的通用函数,因此无需考虑重载,就像对g(3.14)
的调用一样。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.