单一变量存放多种类型的数据 in C++【C++学习笔记】

本文介绍了C++17中的std::variant特性,它允许在一个变量中安全地存储多种类型的数据。通过std::get和std::get_if函数可以访问和判断variant中的数据类型。variant相比union提供了类型安全,避免了未定义行为,但在内存效率上可能略逊一筹。文章还对比了variant与union的区别,并推荐在不牺牲安全性的情况下优先使用std::variant。

摘要生成于 C知道 ,由 DeepSeek-R1 满血版支持, 前往体验 >

77.单一变量存放多种类型的数据

今天的主题是:如何在一个变量中存储多种类型的数据

(这是一个C++17的特性)

如何做到呢?要用到一个叫**std::variant**的东西(variant意思:变种,变形,各种各样的,易变的)

🍅概述variant

它和option很像,它的作用是让我们不用担心处理确切的数据类型,只有一个变量,之后我们在考虑它的具体类型

故我们做的就是指定一个叫std::variant的东西,然后列出它可能的数据类型

std::variant允许你列出所有可能的类型,然后你可能决定它将是什么

🍅具体使用

首先要包含头文件#include <variant>

#include <iostream>
#include <variant>

int main() {
    //列举出可能的类型
    std::variant<std::string, int> data;
    data = "Cherno";
    //访问variant的数据是利用std::get<  >(  )
    std::cout << std::get<std::string>(data) << "\n";
    data = 2;
    std::cout << std::get<int>(data) << "\n";
    return 0;
}

那么如何知道当前的variant中存的是什么东西呢?

利用.index()函数便可

//string的索引是0,int的索引是1
std::variant<std::string, int> data;
data = "Cherno";
std::cout << data.index() << "\n";	//这里会输出0
data = 1;
std::cout << data.index() << "\n";	//这里会输出1

当然,还有更好的方法

便是利用get_if函数

//string的索引是0,int的索引是1
std::variant<std::string, int> data;
data = "Cherno";
//get_if需要接收variant的地址,然后会返回一个指针
//如下面例子,如果data是字符串,则返回一个指向该字符串的指针
//如果不是字符串,则返回一个空指针
auto valuePoint = std::get_if<std::string>(&data);

如果结合一下if,则会更加好用

std::variant<std::string, int> data;
data = "Cherno";
//如果data的值是字符串,则进一步对其进行操作
if (auto valuePoint = std::get_if<std::string>(&data)) {
    std::string &str = *valuePoint;
}

get_if的方法是最推荐的。因为它干净且有用,可读性也高(index返回个01234还得回去猜猜各个索引代表的是什么)

那么variantunion有何不同呢

//如果是union
union {
    double a, int b;
}

则这个union的大小就是最大的类型的大小,即为8个字节

而如果是variant

std::variant<int, double> data;

得到的大小将会是int + double的大小,即是12字节

故此二者的区别就有了

  • union相当于将里面的变量都同一丢在一个内存块里(当然是以最大的类型为标准)
  • 而variant是为你创建了一个结构体或者类,它只是将这多种的类型数据储存为那个类或结构体中的成员,只是看起来更加简洁罢了
所以从技术上讲,union仍然是更有效率和更好的

然而variant更加安全(对于类型),不会造成未定义行为,所以应当去使用它,除非做的是底层优化,非常需要性能

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值