初始化列表和结构化绑定扣歧义C++ 17
我一直回避初始化像下面初始化列表和结构化绑定扣歧义C++ 17
const auto& x = a, y = b;
const int* const x = ptr_1, *const y = ptr_2; // wot
对于参考和指针限定符不同时适用于初始化的原因。诚然它的第一件事情初学者学习一个,与它相关的不确定性让我感觉像下面的更清晰,需要较少的思想读者的结束
const auto& x = a;
const auto& y = b;
用C++ 17和结构绑定我很高兴,看到了很多潜力。 C++ 17取缔了C++ 14和C++ 11未能修复的内容,auto x {1}
是int
而不是std::initializer_list<int>
。但为什么下面的代码不起作用?
const auto& [x, y] {a, b};
const auto& [x, y] = {a, b};
后者符合自动扣除和初始化列表的新规则,右侧的表达式被视为初始化列表。但对于前者编译失败,出现以下错误
initializer for variable '[a, b]' with type 'const auto &' contains multiple expressions
有没有什么办法可以不必诉诸元组,对等的声明x和y与结构化绑定语法?另外为什么上面的代码示例中的前者不适合形成代码?该语法中是否存在歧义?
这种语法只是不支持。您只能解开这对于其std::get
已被重载总类和对象:https://skebanga.github.io/structured-bindings/
不幸的是,你不能真正利用酷扣除引导,因为你要a
,而不是元组成员的引用。因此你必须写出模板参数列表。
#include <tuple>
int main()
{
int a = 1;
int b = 2;
const auto& [x, y] = std::tuple<int&,int&>{a, b};
}
您也可以不像我一样愚蠢,并正确地阅读文档。
#include <tuple>
int main()
{
int a = 1;
int b = 2;
const auto& [x, y] = std::forward_as_tuple(a, b);
}
const auto& [x, y] = std::tie(a, b);
也适用。
结构化绑定可以说是“拆包”的东西。它不是为了结合正常的声明而设计的。尽管有外观,const auto&
既不适用于a
也不适用b
。
你的特定尝试违反[dcl.dcl]/8:
甲简单声明与标识符列表称为 结构绑定声明([dcl.struct.bind])。 [...]的初始化应的形式是“
= assignment-expression
”的,形式为“{ assignment-expression }
”的,或者形式为“(assignment-expression)
”,其中 赋值表达式是阵列或不愈合类的 类型。
int a = 1, b = 2;
const auto bitand <:x, y:> = std::tie(a, b);
这种结构具有约束力的宣言(很)大致相当于
const auto bitand __e = std::tie(a, b); // hidden variable
auto and x = std::get<0>(__e);
auto and y = std::get<1>(__e);
(真实的东西,使用tuple_element
,不auto
)
注:
-
const auto bitand
适用于隐藏变量只有隐藏变量。即使您只写auto
,x
和y
也始终是引用;是否他们的参考对象是const
取决于const
传播属性的初始值设定项的类型。 - 从prvalue初始值设定项临时实现的临时实现将通过参考绑定延长其生命周期。
- 在这个例子中,
x
和y
的类型都是“reference to int”类型;编写x = 1;
是有效的。 - 对
decltype
措辞中的结构化绑定有特殊处理。
这些语义并不让人吃惊,如果我们正在讨论用两个“引用int”成员来解压结构等等,一个const
这样的东西实际上并不影响指示对象的常量。 OTOH,如果你想将结构化的绑定声明用于他们不打算做的事情,那么你会遇到一个不好的惊喜。
'const auto&'是可怕的误导。尝试写'x = 1;'。 –
@ T.C。有趣。任何想法为什么'const'在这里被忽略? –
@HenriMenke它的,因为如果你制作一个'std :: tuple',然后调用'std :: get ',那么'const'不会传播到指向引用的值。当应用于不传播到实际值的指针而是仅传递给指针本身时,它与'const'的问题相同。 –
Curious