floating constant
浮动常数
允许直接在表达式中使用浮点类型的值。
句法
浮点常量是一个非左值表达式,其形式为:
significand exponent(optional) suffix(optional) | | |
---|
有效数字的形式。
whole-number(optional) .(optional) fraction(optional) | | |
---|
指数的形式。
e | E exponent-sign(optional) digit-sequence | (1) | |
---|---|---|
p | P exponent-sign(optional) digit-sequence | (2) | (since C99) |
1)十进制浮点常量的指数语法
2)十六进制浮点常量的指数语法
说明
如果有效数字以字符序列0x或0X开头,则浮点常量是一个十六进制浮点常量。否则,它是一个十进制浮点常量。对于十六进制浮点常量,有效数被解释为十六进制有理数,并且指数的数字序列被解释为必须缩放有效数的2的整数次幂。双d = 0x1.2p3; //十六进制小数1.2(十进制1.125)按2 ^ 3缩放,即9.0 | (自C99以来) |
---|
对于十进制浮点常量,有效数被解释为十进制有理数,并且指数的数字序列被解释为10的整数幂,有效数必须被缩放到该幂。
double d = 1.2e3; // decimal fraction 1.2 scaled by 10^3, that is 1200.0
一个没有任何固定的浮点常量具有类型double
。如果后缀是字母f
或者F
,浮动常数是类型的float
。如果后缀是字母l
或者L
,浮动常数是类型的long double
。
评估浮点常量的结果或者是最接近的可表示值,或者是以实现定义的方式选择的紧邻最接近的可表示值的较大或较小的可表示值(换句话说,翻译期间的默认舍入方向是实现定义的) 。
如果由 FLT_EVAL_METHOD 指示,则浮点常量可能会转换为更多的范围和精度。例如,在表达式中,常数0.1f可能表现为0.1L。 | (自C99以来) |
---|
如果 FLT_RADIX 为2,则评估十六进制浮点常量的结果是由浮点常量表示的精确值,正确地舍入到目标类型。 | (自C99以来) |
---|
如果指数存在且不使用小数部分,则可以省略小数点分隔符:
double x = 1e0; // floating-point 1.0 (period not used)
对于十进制浮点常量,指数部分是可选的。如果省略,则该期间不是可选的,并且必须存在整数或分数。
double x = 1.; // floating-point 1.0 (fractional part optional)
double y = .1; // floating-point 0.1 (whole-number part optional)
For hexadecimal floating constants, the exponent is not optional to avoid ambiguity resulting from an f suffix being mistaken as a hexadecimal digit. | (since C99) |
---|
对于十六进制浮点常量,指数不是可选的,以避免f后缀被误认为十六进制数字而引起的歧义。 | (自C99以来) |
---|
当浮点常量转换为内部表示时,默认的舍入方向和精度有效,即使#pragma STDC FENV_ACCESS
有效(对于字符串的执行时间转换,strtod
也可以使用),浮点异常不会 产生。请注意,这与浮点类型的算术常量表达式不同。
在浮动常量字母是不区分大小写的:0x1.ep+3
与0X1.EP+3
表示相同的浮点值15.0。
指定的小数点setlocale
对浮点常量的语法没有影响:小数点字符始终为句点。
与整数不同,并不是每个浮点值都可以用十进制或甚至十六进制常量语法直接表示:宏 NAN 和 INFINITY 以及诸如nan
提供生成这些特殊值的方式的函数。请注意0x1.FFFFFEp128f
,它可能看起来像一个 IEEE 浮点型NaN,实际上以这种格式溢出到无穷大。
没有负向浮动常量; 一个表达式,如-1.2
算术运算符一元减号应用于浮点常量1.2
。请注意,特殊值负零可以用-0.0
。
例
#include <stdio.h>
int main(void)
{
printf("15.0 = %a\n", 15.0
printf("0x1.ep+3 = %f\n", 0x1.ep+3
// Constants outside the range of type double.
printf("+2.0e+308 --> %g\n", 2.0e+308
printf("+1.0e-324 --> %g\n", 1.0e-324
printf("-1.0e-324 --> %g\n", -1.0e-324
printf("-2.0e+308 --> %g\n", -2.0e+308
}
输出:
15.0 = 0x1.ep+3
0x1.ep+3 = 15.000000
+2.0e+308 --> inf
+1.0e-324 --> 0
-1.0e-324 --> -0
-2.0e+308 --> -inf
参考
- C11 standard (ISO/IEC 9899:2011):