在哪里使用std :: variant over union? [英] Where to use std::variant over union?

查看:108
本文介绍了在哪里使用std :: variant over union?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

请说明工会 std :: variant 有什么区别,以及为什么 std :: variant 是否已引入标准?在什么情况下,我们应该使用 std :: variant 代替老式的 union

Please explain what is the difference between union and std::variant and why std::variant was introduced into the standard? In what situations should we use std::variant over the old-school union?

推荐答案

通常来说,除非出现以下情况之一,否则您最好使用 variant

Generally speaking, you should prefer variant unless one of the following comes up:


  1. 您在作弊。您正在执行类型调整或其他类似UB的操作,但是希望编译器不会破坏您的代码。

  1. You're cheating. You're doing type-punning or other things that are UB but you're hoping your compiler won't break your code.

您正在执行一些操作允许C ++ union 做的伪punnery:在兼容布局的类型之间或在常见的初始序列之间进行转换。

You're doing some of the pseudo-punnery that C++ unions are allowed to do: conversion between layout-compatible types or between common initial sequences.

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

You explicitly need trivial copyability and/or layout compatibility. variant<Ts> are not required to have any particular layout or trivial copyability. unions of standard layout types are standard layout, and unions of trivially copyable types are trivially copyable.

请注意,有建议使变体如果其组件类型是普通可复制的。提议将其作为针对C ++ 17的缺陷报告,因此,此行为将有效地反向移植到C ++ 17中。

Note that there is a proposal to make variant trivially copyable if its component types are trivially copyable. It's proposed as a defect report against C++17, so this behavior would effectively be backported into C++17.

您需要低级支持就地切换对象。对于此类事情使用内存缓冲区并不能提供简单的复制保证,您可以摆脱 union

You need low-level support for in-place switching of objects. Using a memory buffer for such things doesn't provide the trivial copying guarantees that you could get out of a union.

两者之间的基本区别是变体 知道会存储它的类型,而工会希望您从外部进行跟踪。因此,如果尝试在变体中访问错误的项目,则会得到异常或 nullptr 。相比之下,使用工会只是未定义的行为。

The basic difference between the two is that variant knows which type it stores, while union expects you to keep track of that externally. So if you try to access the wrong item in a variant, you get an exception or nullptr. By contrast, doing so with a union is merely undefined behavior.

工会是较低级别的工具,因此仅在绝对需要较低级别的工具时才应使用。

union is a lower-level tool, and thus should only be used when you absolutely need that lower-level.

变体也具有进行访问的机制,这意味着您可以避免使用一堆 if 语句询问如果它是X类型,请执行此操作 。如果是类型Y,则执行该操作,等等。

variant also has machinery for doing visitation, which means you get to avoid having a bunch of if statements where you ask "if it is type X, do this. If it is type Y, do that, etc".

这篇关于在哪里使用std :: variant over union?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆