Function contract specifiers (since C++26)
From cppreference.net
函数契约说明符(前置条件使用 pre 声明,后置条件使用 post 声明)是可应用于函数或lambda表达式声明符的说明符,用于向对应函数引入相应类型的函数契约断言。
它们确保在程序执行期间指定条件保持成立,若条件评估结果为 false 或评估过程因异常退出,则在调试版本中触发违规行为(例如终止程序),为提升性能在发布版本中可忽略这些检查。
目录 |
前置条件
前置条件( pre )是一个谓词, 调用方 必须确保在调用函数或lambda表达式 之前 该条件成立,在调试版本中会进行检查以验证输入或状态。
后置条件
后置条件( post )是一个谓词,要求 被调用方 必须确保在函数或lambda完成 之后 成立,在调试版本中会进行验证以确认输出或状态。
语法
pre
属性
(可选)
(
表达式
)
|
(1) | ||||||||
post
属性
(可选)
(
结果名称
(可选)
谓词
)
|
(2) | ||||||||
| attr | - | 任意数量的 属性 |
| result-name | - |
identifier
:
|
| identifier | - | 关联函数的结果绑定名称 |
| predicate | - | 应求值为 true 的布尔表达式 |
1)
前置条件
2)
后置条件
关键词
注释
| 功能测试宏 | 值 | 标准 | 功能特性 |
|---|---|---|---|
__cpp_contracts
|
202502L
|
(C++26) | 契约 |
示例
-
函数
normalize的前提条件要求调用者传入可归一化的向量。 -
后置条件确保函数
normalize返回归一化后的向量。
运行此代码
#include <array> #include <cmath> #include <concepts> #include <contracts> #include <limits> #include <print> template <std::floating_point T> constexpr auto is_normalizable(const std::array<T, 3>& vector) noexcept { const auto& [x, y, z]{vector}; const auto norm{std::hypot(x, y, z)}; return std::isfinite(norm) && norm > T {0}; } template <std::floating_point T> constexpr auto is_normalized(const std::array<T, 3>& vector) noexcept { const auto& [x, y, z]{vector}; const auto norm{std::hypot(x, y, z)}; constexpr auto tolerance{010 * std::numeric_limits<T>::epsilon()}; if (!is_normalizable(norm)) [[unlikely]] return false; return std::abs(norm - T{1}) <= tolerance; } template <std::floating_point T> constexpr auto normalize(std::array<T, 3> vector) noexcept -> std::array<T, 3> pre(is_normalizable(vector)) post(vector: is_normalized(vector)) { auto& [x, y, z]{vector}; const auto norm{std::hypot(x, y, z)}; x /= norm, y /= norm, z /= norm; return vector; } int main() { const auto v = normalize<float>({0.3, 0.4, 0.5}); std::println("{}", v); const auto w = normalize<float>({0, 0, 0}); // 违反前置和后置条件 std::println("{}", w); }
可能的输出:
[0.4242641, 0.56568545, 0.70710677] [-nan, -nan, -nan]
参考文献
- C++26 标准 (ISO/IEC 14882:2026):
-
- 9.(3+ c ) 函数契约说明符 [dcl.contract]
参见
| 合约断言 (C++26) | 指定在程序执行特定位置必须成立的条件 |
contract_assert
语句
(C++26)
|
在程序执行期间验证内部条件 |