55

我在这里找到了 *C++ 结构化绑定的原始提案。它提出了一种轻松绑定多个返回值的方法,即:

auto {a, b} = minmax(data);

但是现在看到大家都指向了C++17/C++1z的提案语法

auto [a, b] = minmax(data);

既然我知道了“列表是这样写的{就像这个}”,那么有一个新的列表语法吗?为什么?这里的花括号有什么问题?

4

5 回答 5

21

这仍在辩论中。鉴于 [] 和 {} 已经有多少用途,很难确定哪种语法最容易混淆。

“最少混淆”和“最容易解析”也存在冲突的风险。

于 2016-10-30T21:01:25.917 回答
21

西班牙和美国的国家机构提议改回{}语法,因为(P0488R0):

“结构化绑定”提案最初使用大括号“{}”来分隔绑定标识符。在断言它们没有引入任何语法问题的情况下,这些分隔符被更改为括号“[]”。然而,他们最终通过属性和 lambda 引入了句法歧义。鉴于各种建议的修复,原始语法似乎更合适。

因此,仍然有可能最终获得 C++17 的原始语法(我坚信这是大多数用户的首选)。


行程报告的更新

分解声明的原始提案使用auto {a, b, c};上次会议更改为auto [a, b, c]. 此更改颇具争议,一些评论要求将其更改回{}(而其他人则鼓励保留[])。双方都有技术论据([]一旦开始允许嵌套分解,语法可能与属性冲突;{}如果您将概念混入其中并允许使用概念名称而不是 ,则语法可能与统一初始化冲突auto),所以最后这在很大程度上是一个品味问题。clang 实现者确实报告说他们都尝试了这两种方法,并且发现歧义更容易解决[]。最终没有达成一致的改变,所以现状([]语法)仍然存在。

于 2016-11-03T06:43:00.537 回答
16

@SebastianWahl 只评论了一个链接。我将快速总结链接背后的内容。

Chandler Carruth 对这个问题的回答:youtu.be/430o2HMODj4?t=15m50s

auto [a,b,c] = f();

没关系auto。但你也可以这样做:

tuple<int,float,string> [a,b,c] = f();

所以当你使用{...}这将成为

tuple<int,float,string> {a,b,c} = f();  //<<< not C++17

这很糟糕,因为这件作品tuple<int,float,string> {a,b,c}在 C++ 中也有含义,因此很难模棱两可,难以解决。

于 2017-03-30T09:57:55.667 回答
10

从 {} 到 [] 的更改发生在杰克逊维尔之后,是为了响应该会议的评论而做出的。这在p0144r2中有详细说明,其中指出:“因为它在视觉上与用于声明相同类型的多个变量的现有语法更加不同。”

在 2016 年 11 月的会议上,要求更改 {} 原始用法的 NB 评论似乎并未增加共识,使 [] 用法保持不变。至少在春季会议之前。

于 2016-10-31T22:25:31.700 回答
3

对于方括号语法要说的一件事是,它非常类似于 lambda 捕获子句,同样,您不指定变量类型,因为隐含了auto 。IE

auto func = [a, b] {}
auto func = [a=1, b=2.0] {}

这显然不是完全相同的东西,但是当您将其视为“通过理解上下文进行自动捕获的语法”时,它可以工作:

auto [a, b] = std::make_pair(1, 2.0);
于 2017-04-19T07:00:19.220 回答