命名空间
变体
操作

独立和托管实现

来自 cppreference.com
< cpp

C++ 标准定义了两种类型的实现:托管独立 实现。对于托管 实现,C++ 标准要求的标准库头文件集比独立 实现的要多得多。在独立 实现中,执行可能在没有操作系统的环境下进行。

实现的类型是实现定义的。 对于托管实现,宏 __STDC_HOSTED__ 预定义为 1,对于独立实现,预定义为 0(自 C++11 起)

内容

多线程执行和数据竞争 的要求

独立 托管
独立 实现下,是否允许程序拥有多个 执行线程 是实现定义的。 托管 实现下,C++ 程序可以拥有多个 线程 同时运行。
(自 C++11 起)

[编辑] main 函数的要求

独立 托管
独立 实现中,是否需要程序定义 main 函数是实现定义的。启动和终止是实现定义的;启动包含对具有静态存储期的 命名空间作用域 的对象的 构造函数 的执行;终止包含对具有静态 存储期 的对象的 析构函数 的执行。 托管 实现中,程序必须包含一个名为 main 的全局函数。执行程序会在一个 main 执行线程 中启动,在该线程中调用 main 函数,并且在该线程中可能初始化和销毁具有静态 存储期 的变量。

[编辑] 标准库头文件 的要求

独立 实现具有实现定义的头文件集。该集合至少包括下表中的头文件。

对于部分独立头文件,独立实现只需要提供对应概要中的部分实体。

  • 如果实体以 // freestanding 注释,则保证提供。
  • 如果实体(函数或函数模板)以 // freestanding-deleted 注释,则保证提供或删除。
(自 C++26 起)
独立实现所需的头文件
组件 头文件  独立 
语言支持 通用定义 <cstddef> 全部
C 标准库 <cstdlib> 部分
实现属性 <cfloat>
<climits> (自 C++11 起)
<limits>
<version> (自 C++20 起)
全部
整数类型 <cstdint> (自 C++11 起) 全部
动态内存管理 <new> 全部
类型识别 <typeinfo> 全部
源位置 <source_location> (自 C++20 起) 全部
异常处理 <exception> 全部
初始化列表 <initializer_list> (自 C++11 起) 全部
比较 <compare> (自 C++20 起) 全部
协程支持 <coroutine> (自 C++20 起) 全部
其他运行时支持 <cstdarg> 全部
调试支持 <debugging> (自 C++26 起) 全部
概念 <concepts> (自 C++20 起) 全部
诊断 错误编号 <cerrno> (自 C++26 起) 部分
系统错误支持 <system_error> (自 C++26 起) 部分
内存管理  内存 <memory> (自 C++23 起) 部分
元编程 类型特征 <type_traits> (自 C++11 起) 全部
编译时有理数算术  <ratio> (自 C++23 起) 全部
通用实用程序 实用程序组件 <utility> (自 C++23 起) 全部
元组 <tuple> (自 C++23 起) 全部
函数对象 <functional> (自 C++20 起) 部分
原始数值转换 <charconv> (自 C++26 起) 部分
位操作 <bit> (自 C++20 起) 全部
字符串 字符串类 <string> (自 C++26 起) 部分
空终止
序列实用程序
<cstring> (自 C++26 起)
<cwchar> (自 C++26 起)
部分
迭代器 <iterator> (自 C++23 起) 部分
范围 <ranges> (自 C++23 起) 部分
数值 数学函数
用于浮点类型
<cmath> (自 C++26 起) 部分
并发支持 原子 <atomic> (自 C++11 起)     全部[1]
已弃用 的头文件 <ciso646> (直到 C++20)
<cstdalign> (自 C++11 起)(直到 C++20) 
<cstdbool> (自 C++11 起)(直到 C++20)
全部
  1. 对于始终无锁的整数原子类型以及类型别名 std::atomic_signed_lock_freestd::atomic_unsigned_lock_free 的存在,在独立实现中是实现定义的。(自 C++20 起)

[编辑] 说明

一些编译器厂商可能不支持独立实现的全部功能。例如,GCC libstdc++ 在 13 版本之前存在实现和构建问题,而 LLVM libcxx 和 MSVC STL 不支持独立实现。

在 C++23 中,许多功能通过部分头文件成为了独立的。但是,WG21 仍在讨论将来标准中是否会将一些头文件设为独立的。无论如何,像 vectorlistdequemap 这样的容器永远不会是独立的,因为它们依赖于异常和堆。

GCC 13 为独立实现提供了更多头文件,例如 <optional><span><array><bitset>,尽管这些头文件可能不具有可移植性,或者提供的功能与托管实现的功能不同。最好避免在独立环境中使用它们,即使工具链提供了它们。

功能测试 Std 功能
__cpp_lib_freestanding_feature_test_macros 202306L (C++26) 独立功能测试宏
__cpp_lib_freestanding_algorithm 202311L (C++26) 独立的 <algorithm>
__cpp_lib_freestanding_array 202311L (C++26) 独立的 <array>
__cpp_lib_freestanding_char_traits 202306L (C++26) 独立的 std::char_traits
__cpp_lib_freestanding_charconv 202306L (C++26) 独立的 <charconv>
__cpp_lib_freestanding_cstdlib 202306L (C++26) 独立式 <cstdlib>
__cpp_lib_freestanding_cstring 202311L (C++26) 独立式 <cstring>
__cpp_lib_freestanding_cwchar 202306L (C++26) 独立式 <cwchar>
__cpp_lib_freestanding_errc 202306L (C++26) 独立式 std::errc
__cpp_lib_freestanding_expected 202311L (C++26) 独立式 <expected>
__cpp_lib_freestanding_functional 202306L (C++26) 独立式 <functional>
__cpp_lib_freestanding_iterator 202306L (C++26) 独立式 <iterator>
__cpp_lib_freestanding_mdspan 202311L (C++26) 独立式 <mdspan>
__cpp_lib_freestanding_memory 202306L (C++26) 独立式 <memory>
__cpp_lib_freestanding_numeric 202311L (C++26) 独立式 <numeric>
__cpp_lib_freestanding_optional 202311L (C++26) 独立式 <optional>
__cpp_lib_freestanding_ranges 202306L (C++26) 独立式 <ranges>
__cpp_lib_freestanding_ratio 202306L (C++26) 独立式 <ratio>
__cpp_lib_freestanding_string_view 202311L (C++26) 独立式 <string_view>
__cpp_lib_freestanding_tuple 202306L (C++26) 独立式 <tuple>
__cpp_lib_freestanding_utility 202306L (C++26) 独立式 <utility>
__cpp_lib_freestanding_variant 202311L (C++26) 独立式 <variant>

[编辑] 参考资料

  • C++23 标准 (ISO/IEC 14882:2024)
  • 4.1 实现符合性 [intro.compliance] (p: 10)
  • 6.9.2 多线程执行和数据竞争 [intro.multithread] (p: 84)
  • 6.9.3.1 main 函数 [basic.start.main] (p: 89)
  • 16.4.2.5 独立式实现 [compliance] (p: 483)
  • C++20 标准 (ISO/IEC 14882:2020)
  • 4.1 实现符合性 [intro.compliance] (p: 7)
  • 6.9.2 多线程执行和数据竞争 [intro.multithread] (p: 77)
  • 6.9.3.1 main 函数 [basic.start.main] (p: 82)
  • 16.5.1.3 独立式实现 [compliance] (p: 470)
  • C++17 标准 (ISO/IEC 14882:2017)
  • 4.1 实现符合性 [intro.compliance] (p: 5)
  • 4.7 多线程执行和数据竞争 [intro.multithread] (p: 15)
  • 6.6.1 main 函数 [basic.start.main] (p: 66)
  • 20.5.1.3 独立式实现 [compliance] (p: 458)
  • C++14 标准 (ISO/IEC 14882:2014)
  • 1.4 实现符合性 [intro.compliance] (p: 5)
  • 1.10 多线程执行和数据竞争 [intro.multithread] (p: 11)
  • 3.6.1 main 函数 [basic.start.main] (p: 62)
  • 17.6.1.3 独立式实现 [compliance] (p: 441)
  • C++11 标准 (ISO/IEC 14882:2011)
  • 1.4 实现符合性 [intro.compliance] (p: 5)
  • 1.10 多线程执行和数据竞争 [intro.multithread] (p: 11)
  • 3.6.1 main 函数 [basic.start.main] (p: 58)
  • 17.6.1.3 独立式实现 [compliance] (p: 408)
  • C++03 标准 (ISO/IEC 14882:2003)
  • 1.4 实现符合性 [intro.compliance] (p: 3)
  • 3.6.1 main 函数 [basic.start.main] (p: 43)
  • 17.4.1.3 独立式实现 [lib.compliance] (p: 326)

[编辑] 缺陷报告

以下行为变更缺陷报告已追溯应用到先前发布的 C++ 标准。

DR 应用于 发布时的行为 正确行为
CWG 1938 C++98 实现不需要
记录其是否为托管的
将实现类型设置为实现定义的
(因此需要记录)
LWG 3653
(P1642R11)
C++20 <coroutine> 是独立式的,但是
使用 std::hash,它不是
使 <functional> 成为
部分独立式的

[编辑] 参见

C 文档 针对 符合性