13

C++11 让我们可以在联合中使用非 POD 类型,比如我有以下代码;

union
{
    T one;
    V two;
} uny;

在我班的某个地方,一次只有一个成员会活跃,现在我的问题很简单。

  1. uny的默认值是多少?- 不明确的?
  2. 每当我的班级被破坏时,哪些成员(工会内)(如果有的话)将被破坏?
    • 假设我必须 std::typeinfo 来跟踪哪个是活动成员,然后我应该在析构函数中显式调用该成员的析构函数吗?
  3. 有没有人有语言提案的链接,它改变了工会以接受非 POD 类型?
4

3 回答 3

16

你主要是靠自己。标准中的注释解释了这一点(9.5/2):

如果联合的任何非静态数据成员具有重要的默认构造函数 (12.1)、复制构造函数 (12.8)、移动构造函数 (12.8)、复制赋值运算符 (12.8)、移动赋值运算符 (12.8) 或析构函数 ( 12.4),联合的相应成员函数必须是用户提供的,否则它将为联合隐式删除(8.4.3)。

因此,如果任何成员构造函数是非平凡的,则需要为联合编写一个构造函数(如果它们都是平凡的,则默认状态将是未初始化的,例如 for union { int; double; })。如果任何成员有析构函数,则需要为联合体编写析构函数,该析构函数必须负责找出活动元素。

还有一个关于无约束联合的典型用法的进一步说明(9.5/4):

通常,必须使用显式析构函数调用和放置新运算符来更改联合的活动成员。

于 2013-11-04T09:10:07.963 回答
1

联合的替代方案:

std::any/ std::variant (C++17)

boost::any/boost::variant

这些允许使用非 POD 数据类型。

于 2016-10-11T11:13:36.370 回答
0

这是一个棘手的问题。

也许你可以使用这个:

uny un;
new(&un.one) T;

您可以参考 https://en.cppreference.com/w/cpp/language/union

于 2021-11-02T11:30:34.637 回答