我不知道为什么这些代码无法编译。我在Visual c + + 2010和gcc中测试了-std = c ++ 0x。有人提出一些建议吗? 谢谢!
template<typename T>
class Foo
{
public:
void test(const T&){cout<<"const";}
void test( T&){cout<<"non const";}
};
int main()
{
int a;
Foo<int&> f;
}
编译错误:'void Foo :: test(T)':已定义或声明的成员函数
但为什么要编译?
template<typename T> void foo(const T&){cout<<"const"; }
template<typename T> void foo( T&){cout<<"non const"; }
int main()
{
int a;
foo<int&>(a);
}
我读过c ++ 0x文章说:T&amp; &安培; == T&安培;所以const T&amp; &安培; == const T&amp; ?
答案 0 :(得分:13)
我读过c ++ 0x文章说:T&amp; &安培; == T&安培;所以const T&amp; &安培; == const T&amp; ?
实际上,这并没有多大意义。恕我直言,最好将其放入表格中:
T T& const T const T&
---------------------------------------
int int& const int const int&
int& int& int& int&
(1) (2) (1+2)
1: Reference collapsing in action
2: const applies to the reference and is therefore ignored
如果T已经是引用(第2行),则const T
中的const适用于引用而不适用于裁判。但是,在初始化之后你无法让它引用另一个对象的意义上,引用本质上是不变的,所以在这里忽略const
。你可以把它想象成“const崩溃”。 ; - )
答案 1 :(得分:8)
此:
Foo<int&> f;
引发了这种实例化:
class Foo<int&>
{
public:
void test(int&);
void test(int&);
};
const
应用于作为参考的类型是无操作。将它与在参考数据成员上运行的非静态成员函数进行比较:
struct A {
int &ref;
// valid: const member function doesn't treat "ref" as "const int&".
void operate() const {
ref = 0;
}
};
您必须将int
传递给Foo<...>
才能实现目标。
答案 2 :(得分:1)
对于第二个问题,两个实例化的函数具有相同的参数类型,并且都是模板(如果一个是模板,另一个是非模板函数,重载决策将选择后一个),所以重载决策将选择更专业的模板。通常const T&amp;是一种比T&amp;更专业的类型,所以第一个模板函数被调用。