为什么C ++ 20不支持乱序的指定初始化程序?

时间:2018-11-11 15:53:16

标签: c++ c++20 designated-initializer

我在阅读C++ reference时,对本段有疑问:

  

注:乱序指定初始化,嵌套指定   初始化,混合指定的初始值设定项和常规   初始化程序和数组的指定初始化全部   在C编程语言中受支持,但在C ++中是不允许的。

是否有任何技术原因阻止C ++支持乱序的指定初始化?

2 个答案:

答案 0 :(得分:9)

是的,理由在附件C(内容翔实)中进行了介绍 兼容性,特别是[diff.dcl]p10强调我的):

  

受影响的子句:[dcl.init.aggr]更改:在C ++中,指定   初始化支持与相应的相比受到限制   C中的功能。在C ++中,非静态数据成员的指示符   必须按声明顺序指定,数组元素的代号   和嵌套的指示符不受支持,并已指定和   未指定的初始化程序不能在同一初始化程序中混合使用   清单。示例:

struct A { int x, y; };
struct B { struct A a; };
struct A a = {.y = 1, .x = 2};  // valid C, invalid C++
int arr[3] = {[1] = 5};         // valid C, invalid C++
struct B b = {.a.x = 0};        // valid C, invalid C++
struct A c = {.x = 1, 2};       // valid C, invalid C++
     

合理性:在C ++中,成员按相反的构造顺序销毁,并且初始化程序列表的元素按词法顺序求值,因此必须按顺序指定字段初始化程序。   数组指示符与lambda-expression语法冲突。   很少使用嵌套的指示符。

first revision of the proposal也讨论了这个主题:

  

为了满足这些期望,可以保证复制的准确性,我们要求指定人出庭   作为数据成员声明序列的子序列,以便求值顺序   匹配声明顺序,并且在指定的初始化中在文本上也从左到右

您可以获得最新的修订版here

答案 1 :(得分:1)

从 C 中只有一小部分指定的初始化选项是痛苦的。也许将来会得到纠正。目前,一些编译器的严格程度低于 C++20 标准。这段代码:

struct A {int x, y;};
A a = {.y=2, .x=4};

编译时出现警告并在 clang-10.0.0 和更新版本中运行良好(请参阅 https://godbolt.org/z/Ybnzz5chx)。