重载带有“T&&”参数的函数模板通常是一个坏主意,因为它可以绑定到任何东西,但假设我们还是这样做了:
template<typename T>
void func(const T& param)
{
std::cout << "const T&\n";
}
template<typename T>
void func(T&& param)
{
std::cout << "T&&\n";
}
我的理解是,const T&
将为 const 左值的参数调用T&&
重载,而为所有其他参数类型调用重载。但是考虑一下当我们func
使用 const 和非常量内容的数组调用时会发生什么:
int main()
{
int array[5] = {};
const int constArray[5] = {};
func(array); // calls T&& overload
func(constArray); // calls const T& overload
}
VC10、VC11 和 gcc 4.7 同意显示的结果。我的问题是为什么第二次调用会调用const T&
重载。简单的答案是其中constArray
有一个 const,但我认为这太简单了。推导的类型 T (无论选择的模板如何)是“5 个 const int 的数组”,因此重载param
中的类型将是“对 5 个 const int 的 const 数组的引用”。const T&
但是名为 constArray 的数组本身并未声明为 const。那么为什么不func(constArray)
调用T&&
重载,从而产生param
“对 5 个 const int 数组的引用”的类型呢?
这个问题的动机是与c++ template function argument deuce and function resolution中的问题相关的讨论,但我认为该线程在其他问题上偏离了方向,并没有澄清我现在在这里提出的问题。