首页 > 后端开发 > C++ > 正文

c++的std::any和std::variant有什么区别 动态类型容器【详解】

穿越時空
发布: 2025-12-23 16:26:02
原创
589人浏览过
std::any支持运行时任意单类型存储与动态类型检查,std::variant限定编译时预定义的多类型集合并提供静态类型安全和visit模式匹配。

c++的std::any和std::variant有什么区别 动态类型容器【详解】

std::anystd::variant 都是 C++17 引入的类型安全的“泛型容器”,但设计目标和使用场景完全不同:前者支持运行时任意类型(单类型、动态确定),后者限定编译时已知的有限类型集合(多类型、静态枚举)。

核心定位不同:动态 vs 静态类型集合

std::any 是“一个能装任何类型的盒子”,只要满足可复制构造,就能存;类型信息在运行时通过 typeid 保存和检查。它不关心你打算存什么,只保证“存得进、取得出、类型对”。
std::variant 是“一组预定义类型的联合体”,比如 variant,只能存这三种之一,编译器在生成代码时就清楚所有可能分支,支持模式匹配(visit)、无异常赋值、零开销抽象。

造物云营销设计
造物云营销设计

造物云是一个在线3D营销设计平台,0基础也能做电商设计

造物云营销设计 97
查看详情 造物云营销设计

类型安全性与检查方式不同

std::any 的类型检查完全在运行时:
- 存入:any a = 42; // OK
- 取出:int x = any_cast(a); // 成功
- 错误取用:any_cast(a) 会抛 std::bad_any_cast 异常
- 可用 a.type() 获取 type_info,但无法自动 dispatch
std::variant 的类型安全由编译器保障:
- 存入:variant v = "hello"; // OK
- 取出必须显式处理所有可能情况(否则编译失败):
  visit([](auto&& x) { cout   get(v); // 若当前不是 string,抛 bad_variant_access
- 编译期强制穷尽匹配,避免漏处理分支

内存布局与性能特征不同

std::any 内部通常采用小对象优化(SOO)+ 堆分配:小类型(如 int)直接存栈上,大类型(如 vector)堆分配并管理生命周期。有额外虚函数/函数指针开销,且每次取值需运行时类型比对。
std::variant 是纯栈结构,大小为最大成员尺寸 + 少量 tag 字节(通常 1 字节)。无动态分配、无虚调用,visit 分支通常被编译器内联优化,性能接近手写 union + switch。

适用场景对比

用 std::any 当你需要:
- 插件系统中传递用户自定义数据(类型不可预知)
- 实现弱类型脚本桥接(如暴露 C++ 值给 Lua)
- 临时绕过模板限制,且类型仅在运行时决定
用 std::variant 当你需要:
- 表达“非此即彼”的业务状态(如 result、json_value)
- 替代裸 union 或 void*,获得类型安全和自动析构
- 性能敏感路径中实现多态行为(配合 visit + constexpr lambda)
- 编译期可验证的类型契约(IDE 可提示缺失分支)

以上就是c++++的std::any和std::variant有什么区别 动态类型容器【详解】的详细内容,更多请关注php中文网其它相关文章!

相关标签:
c++速学教程(入门到精通)
c++速学教程(入门到精通)

c++怎么学习?c++怎么入门?c++在哪学?c++怎么学才快?不用担心,这里为大家提供了c++速学教程(入门到精通),有需要的小伙伴保存下载就能学习啦!

下载
来源:php中文网
本文内容由网友自发贡献,版权归原作者所有,本站不承担相应法律责任。如您发现有涉嫌抄袭侵权的内容,请联系admin@php.cn
最新问题
开源免费商场系统广告
热门教程
更多>
最新下载
更多>
网站特效
网站源码
网站素材
前端模板
关于我们 免责申明 举报中心 意见反馈 讲师合作 广告合作 最新更新
php中文网:公益在线php培训,帮助PHP学习者快速成长!
关注服务号 技术交流群
PHP中文网订阅号
每天精选资源文章推送

Copyright 2014-2025 https://www.php.cn/ All Rights Reserved | php.cn | 湘ICP备2023035733号