C语言中的printf如何舍入浮点数?

时间:2019-06-11 14:33:04

标签: c floating-point

我正在尝试实现printf,并且想知道printf如何舍入浮点数,因为找不到通用规则

例如,如果输入=> printf("|%.f| |%.1f| |%.2f| |%.5f| |%.12f", 0.000099, 0.000099, 0.000099, 0.000099, 0.000099);

这里是输出=> |0| |0.0| |0.00| |0.00010| |0.000099000000

我使用的是IEEE-754中的方法,因此内存中的浮点数为:0.000098999999999999994037755413067714016506215557456016540527343750

我的问题是我何时以及如何舍入浮点数?

我正在寻找所有浮点数必须遵循的一般规则。

3 个答案:

答案 0 :(得分:3)

不确定$是否确实如此,但这似乎适用于您的示例:

  

加5 /(10 ^(小数点数+1)。然后截断。

您的解释有缺陷:您的C编译器将常量转换为双精度。因此,它没有使用return ( <div> <div className="board-row"> {this.renderSquare(0)} {this.renderSquare(1)} {this.renderSquare(2)} </div> <div className="board-row"> {this.renderSquare(3)} {this.renderSquare(4)} {this.renderSquare(5)} </div> <div className="board-row"> {this.renderSquare(6)} {this.renderSquare(7)} {this.renderSquare(8)} </div> </div> ); ,而是使用了更精确的double等效项。

尝试一下:

printf

输出:

  

| 0 | | 0.0 | | 0.00 | | 0.00010 | | 0.000098999997

答案 1 :(得分:2)

您要解决的问题实际上很难解决

大约30年前,许多现有的printf实现都使用conversion code dtoa.c written by David M. Gay

您可以从以下问题中了解有关此问题的更多信息,该问题并非完全相同:

这些网站:

答案 2 :(得分:2)

C标准在§7.21.6.1p13中提供以下内容:

  

对于e, E, f, F, g, and G转换,如果有效的十进制数字最多为DECIMAL_DIG,则应正确舍入结果。如果有效的十进制位数大于DECIMAL_DIG,但源值可以用DECIMAL_DIG位数精确表示,则结果应为带有尾随零的精确表示。否则,源值将由两个相邻的十进制字符串L<U界定,它们都具有DECIMAL_DIG个有效数字;所得的十进制字符串D的值应满足L ≤ D ≤ U,并额外规定该错误对于当前的舍入方向应具有正确的符号。

但是,该段落是“推荐做法”小节的一部分。 (如果附件F有效,则需要推荐的做法。请参见F.5。)

“正确舍入”由当前舍入方向定义。参见fsetround