ste*_*fen 11 python math floating-point precision python-3.x
我们知道,由于数字的二进制表示,此表达式的计算结果为False(至少在Python中):
0.2 + 0.4 == 0.6
Run Code Online (Sandbox Code Playgroud)
为了能够检查数字错误中的相等性,该模块math提供isclose:
import math
math.isclose(0.2 + 0.4 , 0.6)
Run Code Online (Sandbox Code Playgroud)
最后一个表达式True按预期产生.
现在为什么这个表达式False再次出现?
math.isclose(0.2 + 0.4 - 0.6 , 0.0)
Run Code Online (Sandbox Code Playgroud)
看来,一切相比,0.0是False
math.isclose(1.0e-100 , 0.0)
Run Code Online (Sandbox Code Playgroud)
Dav*_*nan 17
答案可以通过阅读文档来解决.
Run Code Online (Sandbox Code Playgroud)math.isclose(a, b, *, rel_tol=1e-09, abs_tol=0.0)如果值a和b彼此接近则返回True,否则返回False.
根据给定的绝对和相对容差确定两个值是否被认为是接近的.
rel_tol是相对容差 - 它是a和b之间允许的最大差值,相对于a或b的较大绝对值.例如,要设置5%的容差,请传递rel_tol = 0.05.默认容差为1e-09,可确保两个值在大约9个十进制数字内相同.rel_tol必须大于零.
abs_tol是最小绝对容差 - 对于接近零的比较很有用.abs_tol必须至少为零.
如果没有错误发生,结果将是:
Run Code Online (Sandbox Code Playgroud)abs(a-b) <= max(rel_tol * max(abs(a), abs(b)), abs_tol)
您使用默认容差,这意味着使用相对容差检查.上面的等式清楚地表明了为什么你的表达式评估为false.
考虑问题中的最终表达:
math.isclose(1.0e-100 , 0.0)
Run Code Online (Sandbox Code Playgroud)
将这些值插入文档中的表达式,我们有
1.0e-100 <= max(1.0e-9 * 1.0e-100, 0.0)
Run Code Online (Sandbox Code Playgroud)
我认为显而易见的是,在执行相对容差比较时,使用默认容差,不会将非零值视为接近零.
对于非常小的值,您应该使用绝对容差.
或者您应该重新编写测试以避免与零进行比较.
| 归档时间: |
|
| 查看次数: |
11315 次 |
| 最近记录: |