【发布时间】:2018-10-28 13:13:06
【问题描述】:
我最近阅读了关于联合默认构造函数的描述: Default Constructor
有如下规则:
块引用 删除了隐式声明的默认构造函数: [...] T 是一个联合,其中至少有一个变体成员具有非平凡的默认构造函数,并且 T 的任何变体成员都没有默认成员初始化器。[...]
然后我决定做一个练习并验证规则。
struct Member {
public:
// Member() : mX(0) {}
virtual int GetX() {
return mX;
}
int mX;
};
union DefaultConstructor {
int mA;
Member mMember;
int GetA();
};
使用 gcc v5.3.1(我知道它已经很老了)我收到了预期的错误:
> ../src/DefaultConstrcutors.cpp: In function ‘void
> Test_DefaultConstructors()’: ../src/DefaultConstrcutors.cpp:26:22:
> error: use of deleted function
> ‘DefaultConstructor::DefaultConstructor()’ DefaultConstructor foo;
> ^ In file included from ../src/DefaultConstrcutors.cpp:19:0:
> ../src/DefaultConstructors.h:155:7: note:
> ‘DefaultConstructor::DefaultConstructor()’ is implicitly deleted
> because the default definition would be ill-formed: union
> DefaultConstructor {
> ^ ../src/DefaultConstructors.h:157:10: error: union member ‘DefaultConstructor::mMember’ with non-trivial ‘Member::Member()’
> Member mMember;
> ^
好的,所以根据规则,如果我为变体成员提供默认成员初始化程序,那么它应该可以编译。所以我将联合定义更改为:
union DefaultConstructor {
int mA = 0;
Member mMember;
int GetA();
};
现在它应该可以编译了,但我收到了同样的错误。
下一步是为 mMember 而不是 mA 提供默认初始化程序(只有一个联合变体成员可能有默认初始化程序)。
union DefaultConstructor {
int mA;
Member mMember{};
int GetA();
};
现在它可以编译了。
问题是:为什么它没有在第二种情况下编译,当 mA 有默认初始化程序时?根据上述规则,应该是可以的。这里提供了更多类似的规则:Union declaration
如果联合包含具有非平凡数据成员的非静态数据成员 默认构造函数,union的默认构造函数被删除 默认情况下,除非联合的变体成员具有默认成员 初始化器。
有人知道为什么它不起作用吗?
您好, 彼得
【问题讨论】:
标签: c++ c++11 language-lawyer unions default-constructor