constexpr 使计算在编译期完成,生成真正常量;要求变量或函数入参均为编译期常量,支持数组大小、模板参数等场景,并区别于 const(运行时只读)和 consteval(强制仅编译期调用)。

constexpr 让你把计算搬到编译期完成,生成真正的常量,不是运行时才确定的“只读变量”。
让变量成为编译期常量
加了 constexpr 的变量,必须在编译期就能算出值,否则报错。它比 const 更严格——const 只保证不修改,值可以来自运行时(比如函数返回);而 constexpr 强制要求值已知、不可变、可参与编译期逻辑。
- int x = 5; constexpr int y = x * 2; → 错误:x 不是编译期常量
- constexpr int a = 10; constexpr int b = a + 3; → 正确:所有值都确定,b 就是 13,存进符号表,不占运行时内存
让函数支持编译期求值
标记为 constexpr 的函数,不等于“只能在编译期调用”,而是“如果入参都是编译期常量,就尝试在编译期算出结果”。它写法受限(C++14 后宽松很多),但好处明显:
- 能用在需要常量表达式的地方:数组大小、模板非类型参数、case 标签等
- 避免重复运行时计算:同一个 constexpr 函数被多处以常量调用,编译器只算一次
- 例如:constexpr int square(int n) { return n * n; } int arr[square(5)]; → 合法,arr 是长度为 25 的数组
让类和构造函数参与编译期构建
C++11 起支持 constexpr 构造函数,只要所有成员都能用常量初始化,整个对象就能是编译期常量。C++20 还允许 constexpr 成员函数中使用循环、局部变量甚至 try-catch(有限制)。
立即学习“C++免费学习笔记(深入)”;
- 常见用途:定义编译期字符串、固定大小容器、数学常量类型(如 constexpr Vec3{1,0,0})
- 关键点:所有数据成员必须是字面类型(literal type),且构造过程不能有副作用
和 const、consteval 的区别
const 是运行时只读语义;constexpr 是编译期可求值能力;consteval(C++20)更进一步——强制只能在编译期调用,哪怕传入运行时值也会编译失败。
- 想写一个“保证不产生运行时开销”的工具函数?用 constexpr
- 想确保某个值绝对进符号表、零成本?优先声明为 constexpr 变量
- 想彻底禁止运行时调用(比如加密密钥生成逻辑)?选 consteval
基本上就这些。它不是语法糖,是让编译器“看懂你的意图”,从而优化、验证、甚至提前报错的关键机制。









