哪里使用std :: variant而不是union?

时间:2017-02-07 05:23:35

标签: c++ c++17

请解释unionstd::variant之间的区别以及为什么std::variant被引入标准?我们应该在什么情况下使用std::variant而不是旧学校union

1 个答案:

答案 0 :(得分:61)

一般来说,除非出现以下情况之一,否则您应该更喜欢variant

  1. 你在作弊。您正在进行类型惩罚或UB的其他事情,但您希望您的编译器不会破坏您的代码。

  2. 你正在做一些C ++ union被允许做的伪惩罚:在布局兼容类型之间或在常见的初始序列之间进行转换。

  3. 您明确需要简单的可复制性和/或布局兼容性。 variant<Ts>不需要具有任何特定布局或简单的可复制性。 unions标准布局类型是标准布局,而union的普通可复制类型是可以轻易复制的。

    请注意a proposal to make variant trivially copyable if its component types are trivially copyable。它被提议作为针对C ++ 17的缺陷报告,因此这种行为将被有效地反向移植到C ++ 17中。

  4. 您需要对对象的就地切换提供低级支持。使用内存缓冲区进行此类操作并不能提供琐碎的复制保证,您可以放弃union

  5. 两者之间的基本区别在于variant 知道它存储的类型,而union期望您在外部跟踪它。因此,如果您尝试访问variant中的错误项目,则会收到例外或nullptr。相比之下,使用union这样做只是未定义的行为。

    union是一个较低级别的工具,因此只应在绝对需要较低级别时使用。

    variant也有进行访问的机制,这意味着你可以避免在你要求的情况下发出一堆if语句,如果它是X型,请执行此操作。如果是Y型,那么就这样做,等等#34;。