以下代码片段摘自cppref:
std::tuple<int, int&> f();
auto [x, y] = f();
// decltype(x) is int
// decltype(y) is int&
const auto [z, w] = f();
// decltype(z) is const int
// decltype(w) is int&
我的问题在最后一行:
为什么 是 decltype(w)
int&
而不是 const int&
?
Jarod42回答了评论中的问题,让我在这里引用标准的相关部分,来自 [dcl.struct.bind]¹:
给定由 std::tuple_element::type 指定的类型 Ti,变量以类型“对 Ti”的唯一名称 ri 的形式引入,使用初始化程序 ([dcl.init.ref]) 进行初始化,其中引用为如果初始值设定项是左值,则为左值引用,否则为右值引用。每个 vi 是一个类型为 Ti 的左值的名称,它指向绑定到 ri 的对象;引用的类型是 Ti。
因此,在 中,const auto [z, w] = f();
你const T1
有T1
存在int
和const T2
存在。当修改左边的内容时,这变成并导致.T2
int&
const
int& const
int&
请注意,仅在模板参数替换中int& const
才有int&
可能,即,这不会编译:
int n = 42;
int& const doesntWork = n; // Error: 'const' qualifiers cannot be applied to 'int&'
但这确实:
template <class T> void f(const T t)
{
++t;
}
int n = 42;
f<int&>(n);
int& const
发生与上述相同的收缩int&
的地方。
¹ 感谢@cpplearner 将我指向此处的确切段落。
它将是引用本身,而不是 const 的引用值。由于无论如何引用都不可修改,因此没有常量引用之类的东西。