Python四舍五入错误与浮点数字

我不知道这是否是一个明显的错误,但是在运行Python脚本来改变模拟参数时,我意识到delta = 0.29和delta = 0.58的结果丢失了。 在调查中,我注意到下面的Python代码:

for i_delta in range(0, 101, 1): delta = float(i_delta) / 100 (...) filename = 'foo' + str(int(delta * 100)) + '.dat' 

生成相同的文件delta = 0.28和0.29,与.57和.58相同,原因是python返回float(29)/ 100为0.28999999999999998。 但是这不是一个系统性的错误,不是每个整数都有的。 所以我创build了下面的Python脚本:

 import sys n = int(sys.argv[1]) for i in range(0, n + 1): a = int(100 * (float(i) / 100)) if i != a: print i, a 

而且我看不到在这个舍入错误发生的数字中的任何模式。 为什么会发生这些特定的数字?

任何不能用精确的2的幂来构造的数字不能完全表示为浮点数; 它需要近似。 有时最接近的近似值会小于实际值。

阅读每位计算机科学家应该了解的浮点运算 。

由于浮点数的性质,它非常有名。

如果你想做十进制算术而不是浮点算术有库来做到这一点。

例如,

 >>> from decimal import Decimal >>> Decimal(29)/Decimal(100) Decimal('0.29') >>> Decimal('0.29')*100 Decimal('29') >>> int(Decimal('29')) 29 

一般来说,小数可能会过大,在极less数情况下,如果数字不具有有限的小数表示forms(例如,分母不是1或不能被2或5整除的分数 – 十进制基数(10))。 例如:

 >>> s = Decimal(7) >>> Decimal(1)/s/s/s/s/s/s/s*s*s*s*s*s*s*s Decimal('0.9999999999999999999999999996') >>> int(Decimal('0.9999999999999999999999999996')) 0 

所以,除非你想要一个floor函数,否则在把浮点数转换为整数之前总是最好的。

 >>> int(1.9999) 1 >>> int(round(1.999)) 2 

另一种select是使用分数库中的分数类,它不近似。 (它只是加/减和乘以整数的分子和分母必要)。