采用参数包的两个函数的重载分辨率

Ton*_*vel 2 c++ templates reference variadic-templates c++11

请考虑以下两个重载:

template<typename T, typename ...Args>
void f(std::vector<T>&& v, Args&& ...args)
{
    std::cout << "f taking a vector + parameter pack\n";
}

template<typename ...Args>
void f(Args&& ...args)
{
    std::cout << "f taking a parameter pack\n";
}
Run Code Online (Sandbox Code Playgroud)

现在,对于以下片段,选择了预期的重载:

std::vector<int> v{1, 2, 3};
f(std::move(v), 3.0);
Run Code Online (Sandbox Code Playgroud)

(输出:f采用矢量+参数包)

对于以下情况,选择第二个重载:

std::vector<int> v{1, 2, 3};
f(v, 3.0);
Run Code Online (Sandbox Code Playgroud)

(输出:f参数包)

通用参考矢量参数也绑定到左值参考那么为什么只有参数包的重载在这种情况下受到青睐呢?更新:请参阅接受的答案,假设向量参数是通用/转发引用是错误的.

son*_*yao 7

通用参考矢量参数也绑定到左值参考

不,这不是一个普遍的参考.

4)如果P是对cv非限定模板参数(所谓的"转发引用")的右值引用,并且相应的函数调用参数是左值,则使用对A的类型左值引用代替A进行推导(注意:这是std :: forward操作的基础注意:在类模板推导中,类模板的模板参数永远不是转发引用(因为C++ 17)):

因此对于

template<typename T, typename ...Args>
void f(std::vector<T>&& v, Args&& ...args)
Run Code Online (Sandbox Code Playgroud)

请注意,这v不是模板参数的右值参考T,但是std::vector<T>.所以v"只是"一个右值参考,然后不能绑定到左值.