浮点字面量
浮点字面量定义了一个在源代码文件中指定其值的编译时常量。
语法
1 | 数字序列 | 十进制指数后缀 | (可选) | |||||||
2 | 数字序列 | . | 十进制指数 | (可选) | 后缀 | (可选) | ||||
3 | 数字序列 | (可选) | . | 数字序列 | 十进制指数 | (可选) | 后缀 | (可选) | ||
4 | 0x|0X | 十六进制数字序列 | 十六进制指数后缀 | (可选) | (自 C++17 起) | |||||
5 | 0x|0X | 十六进制数字序列 | . | 十六进制指数后缀 | (可选) | (自 C++17 起) | ||||
6 | 0x|0X | 十六进制数字序列 | (可选) | . | 十六进制数字序列 | 十六进制指数后缀 | (可选) | (自 C++17 起) |
- 数字序列表示一个没有小数点的整数,在这种情况下指数不是可选的:
1e10
,1e-5L
。 - 数字序列表示一个有小数点的整数,在这种情况下指数是可选的:
1.
,1.e-2
。 - 数字序列表示一个分数。指数是可选的:
3.14
,.1f
,0.1e-1L
。 - 表示一个没有基数分隔符的整数的十六进制数字序列。对于十六进制浮点文字量,指数永远是必需的:
0x1ffp10
,0X0p-1
。 - 表示一个有基数分隔符的整数的十六进制数字序列。对于十六进制浮点文字量,指数永远是必需的:
0x1.p0
,0xf.p-1
。 - 表示一个有基数分隔符的分数的十六进制数字序列。对于十六进制浮点文字量,指数永远是必需的:
0x0.123p-1
,0xa.bp10l.
。
十进制指数的格式为
e | E | 指数符号 (可选) 数字序列 |
---|
十六进制指数的格式为
p | P | 指数符号 (可选) 数字序列 (自 C++17 起) |
---|
指数符号,如果存在,则为 +
或 -
。
后缀,如果存在,则为 f, l, F, L, f16, f32, f64, f128, bf16, F16, F32, F64, F128, BF16 (自 C++23 起) 之一。后缀决定了浮点文字量的类型。
- (无后缀) 定义
double
。 - f F 定义
float
。 - l L 定义
long double
。
- f16 F16 定义 std::float16_t
- f32 F32 定义 std::float32_t
- f64 F64 定义 std::float64_t
- f128 F128 定义 std::float128_t
- bf16 BF16 定义 std::bfloat16_t
'
可以插入到数字之间作为分隔符;在确定文字量值时,它们会被忽略。 (自 C++14 起)解释
使用十进制科学计数法,这意味着浮点文字量的值为有效数字乘以 10 的 十进制指数次幂。例如,123e4
的数学含义是 123×104。
如果浮点文字量以字符序列 0x
或 0X
开头,则该浮点文字量是十六进制浮点文字量。否则,它是十进制浮点文字量。
对于十六进制浮点文字量,有效数字被解释为十六进制有理数,并且指数的数字序列被解释为 2 的(十进制)整数幂,有效数字需要乘以该幂进行缩放。
double d = 0x1.4p3;// hex fraction 1.4 (decimal 1.25) scaled by 23, that is 10.0
备注
直到 C++17,十六进制浮点文字量都不是 C++ 的一部分,尽管自 C++11 起就可以被 I/O 函数解析和打印:当启用 std::hexfloat 时,C++ I/O 流和 C I/O 流:std::printf, std::scanf 等。有关格式描述,请参阅 std::strtof。
功能测试宏 | 值 | 标准 | 注释 |
---|---|---|---|
__cpp_hex_float | 201603L | (C++17) | 十六进制浮点文字量 |
示例
#include <iomanip>
#include <iostream>
#include <limits>
#include <typeinfo>
#define OUT(x) '\n' << std::setw(16) << #x << x
int main()
{
std::cout
<< "Literal" "\t" "Printed value" << std::left
<< OUT( 58. ) // double
<< OUT( 4e2 ) // double
<< OUT( 123.456e-67 ) // double
<< OUT( 123.456e-67f ) // float, truncated to zero
<< OUT( .1E4f ) // float
<< OUT( 0x10.1p0 ) // double
<< OUT( 0x1p5 ) // double
<< OUT( 0x1e5 ) // integer literal, not floating-point
<< OUT( 3.14'15'92 ) // double, single quotes ignored (C++14)
<< OUT( 1.18e-4932l ) // long double
<< std::setprecision(39)
<< OUT( 3.4028234e38f ) // float
<< OUT( 3.4028234e38 ) // double
<< OUT( 3.4028234e38l ) // long double
<< '\n';
static_assert(3.4028234e38f == std::numeric_limits<float>::max());
static_assert(3.4028234e38f == // ends with 4
3.4028235e38f); // ends with 5
static_assert(3.4028234e38 != // ends with 4
3.4028235e38); // ends with 5
// Both floating-point constants below are 3.4028234e38
static_assert(3.4028234e38f != // a float (then promoted to double)
3.4028234e38); // a double
}
Literal Printed value
58. 58
4e2 400
123.456e-67 1.23456e-65
123.456e-67f 0
.1E4f 1000
0x10.1p0 16.0625
0x1p5 32
0x1e5 485
3.14'15'92 3.14159
1.18e-4932l 1.18e-4932
3.4028234e38f 340282346638528859811704183484516925440
3.4028234e38 340282339999999992395853996843190976512
3.4028234e38l 340282339999999999995912555211526242304
参考文献
- C++23 标准 (ISO/IEC 14882:2023)
- 5.13.4 浮点文字量 [lex.fcon]
- C++20 标准 (ISO/IEC 14882:2020)
- 5.13.4 浮点文字量 [lex.fcon]
- C++17 标准 (ISO/IEC 14882:2017)
- 5.13.4 浮点文字量 [lex.fcon]
- C++14 标准 (ISO/IEC 14882:2014)
- 2.14.4 浮点文字量 [lex.fcon]
- C++11 标准 (ISO/IEC 14882:2011)
- 2.14.4 浮点文字量 [lex.fcon]
- C++98 标准 (ISO/IEC 14882:1998)
- 2.13.3 浮点文字量 [lex.fcon]