此主题可能存在,但是指出此特定问题的方式令人困惑。
我有以下代码 - 第一个用于hpp文件,第三个用于impl文件,最后一个用于cpp。如果我删除注释掉的代码片段,则由于我无法理解的原因而无法编译。
为什么编译器不会抱怨我拥有的其他专业,或者为什么不确定第45行是否是我的代码所在?
错误:
test.cpp:45:23: error: no function template matches function template specialization 'foo'
int const A<int,int>::foo(int const & rhs) {
^
test.cpp:58:5: error: call to 'foo' is ambiguous
A<int, int>::foo( test_int );
^~~~~~~~~~~~~~~~
test.cpp:21:22: note: candidate function
static int const foo(int const & rhs);
^
test.cpp:45:23: note: candidate function
int const A<int,int>::foo(int const & rhs) {
^
2 errors generated.
代码:
#include <iostream>
template <typename X, typename Y>
struct A {
static X const foo(Y const & rhs);
};
template <typename X>
struct A<X,int> {
static X const foo(int const & rhs);
};
template <typename Y>
struct A<int, Y> {
static int const foo(Y const & rhs);
};
template <>
struct A<int,int> {
static int const foo(int const & rhs);
};
//----------------------------------------
template <typename X, typename Y>
X const A<X,Y>::foo(Y const & rhs) {
X ret;
return ret;
};
template <typename X>
X const A<X,int>::foo(int const & rhs) {
X ret;
return ret;
};
template <typename Y>
int const A<int, Y>::foo(Y const & rhs) {
return 42;
};
//If I uncomment the following line, the compiler barfs
//template <>
int const A<int,int>::foo(int const & rhs) {
return rhs;
};
int main() {
std::string test_str;
int test_int;
A<int,std::string>::foo( test_str );
A<std::string,int>::foo( test_int );
A<std::string,std::string>::foo( test_str );
A<int, int>::foo( test_int );
};
答案 0 :(得分:1)
完整的专业化不是模板,而是类。当您输入:
template <>
int const A<int,int>::foo(int const & rhs) {
return rhs;
};
编译器发现您想要专门化(template <>
)带有两个参数的模板A
的成员函数。您尝试专门化的成员是模板的特化,其中两个参数都是int
。编译器尝试找到最佳匹配但无法找到它,因为有两个同样好的候选者:A<X,int>
和A<int,Y>
可以使用该成员函数专门化。那时它放弃了。
由于您要提供的是A<int,int>
成员的定义,并且这是一个完整的专业化(不再是模板),您需要使用通常的语法: return type :: member (参数):
int const A<int,int>::foo(int const & rhs) {
return rhs;
};