AFAIK,下面的代码不应该编译,但它可以在 clang 和 GCC 中编译。我在这里错过了什么?

AFAIK, the code below shouldn't compile, but it does in clang and GCC. What am I missing here?

本文关键字:编译 GCC 在这里 什么 错过了 clang 代码 不应该 AFAIK      更新时间:2023-10-16

下面的代码显示了一个类似并集的类,该类具有一个非平凡的默认构造函数(成员y大括号或相等的初始化器初始化),因此,如果默认了此类的默认构造函数,则应根据§12.1/5第一个要点将其删除。也就是说,声明T t;不应该编译,因为union T没有默认构造函数。但是代码是在clang和GCC中编译和执行的。

#include <iostream>
union T
{
    int y{1};
    float x;
    char c;
    T() = default;
};
int main()
{
    T t;
    std::cout << t.y << 'n';
}

编辑

我上面的问题从一开始就错了,因为并集T是而不是一个类并集。我刚刚知道C++11中的§9.5/8,它说:

的并集是一个并集或具有匿名并集的类作为直接成员。类X的并集有一组变体成员。如果X是并集,则其变体成员是非静态数据成员;否则,它的变体成员是所有的非静态数据成员X.成员的匿名工会

现在,考虑下面的片段。它没有编译,因为联合的默认构造函数已被删除。但我仍然不知道§12.1/5中的哪个要点对这个结果负责。再次注意,并集不是类的并集,因此,§12.1/5中的第一个要点不适用。但这就是clang和GCC中错误信息所说的。请参阅实例。

#include <iostream>
union T{
    int y;
    struct A{ int i; A():i{1} {} } a;
};
int main()
{
    T t;
    std::cout << t.a.i << 'n';
}

项目符号为

X是一个类并集,它有一个具有非平凡的变量成员默认构造函数

被解析为

X是一个类似并集的类,它具有(一个具有非平凡默认构造函数)

即,"具有非平凡的默认构造函数"适用于变体成员的类型,而不是X