【发布时间】:2015-02-09 08:56:01
【问题描述】:
#include <iostream>
struct A {};
struct B : public A {};
template<typename T>
void foo(const T &x) { std::cout << "Called template" << std::endl; }
void foo(const A &a) { std::cout << "Called A" << std::endl; }
int main()
{
foo(A());
foo(B());
return 0;
}
打印出来:
Called A
Called template
我的印象是总是会选择合适的非模板函数而不是模板函数。有人可以向我解释导致这个有点令人惊讶的结果的解决步骤吗?
【问题讨论】:
-
好吧,这里有一个猜测:
B继承自A,但它不是A。因此,当编译器执行重载决议时,它首先寻找一个接受B的函数,而void foo(const A &a)不符合这个标准。但是,模板函数确实适合它,因为T可以成为B。所以,void foo(const T &x)是首选。无论如何,这与overload-resolution标签描述完美匹配:"... 它的规则错综复杂,而且常常令人惊讶,即使对于有经验的用户也是如此。" 所以,确实如此 =)
标签: c++ templates overload-resolution