std:: optional
|
定义于头文件
<optional>
|
||
|
template
<
class
T
>
class optional ; |
(C++17 起) | |
类模板
std::optional
管理一个可选的包含值,即一个可能存在也可能不存在的值。
optional
的一个常见用例是可能失败的函数返回值。与其他方法(如
std::
pair
<
T,
bool
>
)相比,
optional
能很好地处理构造成本高昂的对象,并且更具可读性,因为其意图被明确表达。
在任何给定时间点,
optional
的实例要么
包含一个值
,要么
不包含任何值
。
若
optional
包含值,该值保证被
嵌套在
optional
对象内部。因此,
optional
对象模拟的是对象而非指针,即便定义了
operator*()
和
operator->()
也是如此。
当类型为
optional<T>
的对象被
上下文转换为
bool
时,若该对象包含值则转换返回
true
,若不包含值则返回
false
。
在以下条件下,
optional
对象包含值:
-
该对象通过类型为
T的值或另一个包含值的optional进行初始化/赋值。
在以下情况下对象不包含值:
- 对象被默认初始化。
-
对象通过类型为
std::nullopt_t
的值或不包含值的
optional对象进行初始化/赋值。 - 成员函数 reset() 被调用。
|
|
(since C++26) |
不存在可选的引用、函数、数组或(可能带有 cv 限定符的)
void
类型;若程序使用此类类型实例化
optional
则属于病式构造。此外,若程序使用(可能带有 cv 限定符的)标签类型
std::nullopt_t
或
std::in_place_t
实例化
optional
,该程序同样属于病式构造。
目录 |
模板参数
| T | - | 用于管理初始化状态的值的类型。该类型必须满足 Destructible 要求(特别地,不允许数组和引用类型)。 |
嵌套类型
| 类型 | 定义 |
value_type
|
T
|
iterator
(C++26 起)
|
实现定义的
LegacyRandomAccessIterator
、
ConstexprIterator
和
contiguous_iterator
,其
value_type
和
reference
分别为
std::
remove_cv_t
<
T
>
和
T
&
。
|
const_iterator
(C++26 起)
|
实现定义的
LegacyRandomAccessIterator
、
ConstexprIterator
和
contiguous_iterator
,其
value_type
和
reference
分别为
std::
remove_cv_t
<
T
>
和
const
T
&
。
|
所有对
容器
迭代器类型的要求同样适用于
optional
的
iterator
类型。
数据成员
T*
val
|
指向所含对象的指针(若存在)
( 仅用于说明的成员对象* ) |
成员函数
构造
optional
对象
(公开成员函数) |
|
|
销毁所含值(如果存在)
(公开成员函数) |
|
|
赋值内容
(公开成员函数) |
|
迭代器 |
|
|
(C++26)
|
返回指向起始位置的迭代器
(公开成员函数) |
|
(C++26)
|
返回指向末尾位置的迭代器
(公开成员函数) |
观察器 |
|
|
访问所含值
(公开成员函数) |
|
|
检查对象是否包含值
(公开成员函数) |
|
|
返回所含值
(公开成员函数) |
|
|
若可用则返回所含值,否则返回另一值
(公开成员函数) |
|
单子操作 |
|
|
(C++23)
|
若存在值则返回给定函数对所含值的处理结果,否则返回空
optional
(公开成员函数) |
|
(C++23)
|
若存在值则返回包含转换后所含值的
optional
,否则返回空
optional
(公开成员函数) |
|
(C++23)
|
若包含值则返回
optional
本身,否则返回给定函数的处理结果
(公开成员函数) |
修改器 |
|
|
交换内容
(公开成员函数) |
|
|
销毁任何所含值
(公开成员函数) |
|
|
原位构造所含值
(公开成员函数) |
|
非成员函数
|
(C++17)
(C++17)
(C++17)
(C++17)
(C++17)
(C++17)
(C++20)
|
比较
optional
对象
(函数模板) |
|
(C++17)
|
创建
optional
对象
(函数模板) |
|
(C++17)
|
特化
std::swap
算法
(函数模板) |
辅助类
|
(C++17)
|
std::optional
的哈希支持
(类模板特化) |
|
(C++17)
|
表示不包含值的
std::optional
的指示器
(类) |
|
(C++17)
|
指示对不包含值的 optional 进行已检查访问时引发的异常
(类) |
辅助工具
|
(C++17)
|
nullopt_t
类型的对象
(常量) |
|
原位构造标签
(标签) |
辅助特化
|
template
<
class
T
>
constexpr bool ranges:: enable_view < std :: optional < T >> = true ; |
(C++26 起) | |
此特化的
ranges::enable_view
使
optional
满足
view
要求。
|
template
<
class
T
>
constexpr auto format_kind < std :: optional < T >> = range_format :: disabled ; |
(自 C++26 起) | |
此
format_kind
的特化会禁用
optional
的
范围格式化支持
。
推导指引
注释
| 功能测试 宏 | 值 | 标准 | 功能特性 |
|---|---|---|---|
__cpp_lib_optional
|
201606L
|
(C++17) |
std::optional
|
202106L
|
(C++23)
(DR20) |
完全 constexpr 化 | |
202110L
|
(C++23) | 单子操作 | |
__cpp_lib_optional_range_support
|
202406L
|
(C++26) |
std::optional
的范围支持
|
示例
#include <iostream> #include <optional> #include <string> // optional 可用作可能失败的工厂函数的返回类型 std::optional<std::string> create(bool b) { if (b) return "Godzilla"; return {}; } // std::nullopt 可用于创建任意(空)std::optional auto create2(bool b) { return b ? std::optional<std::string>{"Godzilla"} : std::nullopt; } int main() { std::cout << "create(false) returned " << create(false).value_or("empty") << '\n'; // 返回 optional 的工厂函数可用作 while 和 if 的条件 if (auto str = create2(true)) std::cout << "create2(true) returned " << *str << '\n'; }
输出:
create(false) returned empty create2(true) returned Godzilla
缺陷报告
下列行为变更缺陷报告被追溯应用于先前发布的 C++ 标准。
| 缺陷报告 | 应用于 | 发布时的行为 | 正确行为 |
|---|---|---|---|
| LWG 4141 | C++17 |
存储分配的要求
存在歧义 |
被包含的对象必须
嵌套在
optional
对象内部
|
参见
|
(C++17)
|
类型安全的可辨识联合
(类模板) |
|
(C++17)
|
可容纳任意
CopyConstructible
类型实例的对象
(类) |
|
(C++23)
|
包含期望值或错误值的包装器
(类模板) |
包含指定值的单个元素的
view
(类模板) (定制点对象) |
|
|
(C++20)
|
不包含任何元素的空
view
(类模板) (变量模板) |