用于确定两个数字在舍入到 n 个有效十进制数字时是否几乎相等的函数
问题描述
我被要求测试第 3 方提供的库.众所周知,该库精确到 n 个有效数字.任何不太重要的错误都可以安全地忽略.我想写一个函数来帮助我比较结果:
I have been asked to test a library provided by a 3rd party. The library is known to be accurate to n significant figures. Any less-significant errors can safely be ignored. I want to write a function to help me compare the results:
def nearlyequal( a, b, sigfig=5 ):
此函数的目的是确定两个浮点数(a 和 b)是否近似相等.如果 a==b(完全匹配)或者如果 a 和 b 在以十进制形式写入时舍入到 sigfig 有效数字时具有相同的值,则该函数将返回 True.
The purpose of this function is to determine if two floating-point numbers (a and b) are approximately equal. The function will return True if a==b (exact match) or if a and b have the same value when rounded to sigfig significant-figures when written in decimal.
任何人都可以提出一个好的实施方案吗?我写了一个迷你单元测试.除非你能在我的测试中看到一个错误,否则一个好的实现应该通过以下:
Can anybody suggest a good implementation? I've written a mini unit-test. Unless you can see a bug in my tests then a good implementation should pass the following:
assert nearlyequal(1, 1, 5)
assert nearlyequal(1.0, 1.0, 5)
assert nearlyequal(1.0, 1.0, 5)
assert nearlyequal(-1e-9, 1e-9, 5)
assert nearlyequal(1e9, 1e9 + 1 , 5)
assert not nearlyequal( 1e4, 1e4 + 1, 5)
assert nearlyequal( 0.0, 1e-15, 5 )
assert not nearlyequal( 0.0, 1e-4, 6 )
补充说明:
- 值 a 和 b 可能是 int、float 或 numpy.float64 类型.值 a 和 b 将始终属于同一类型.转换不会给函数带来额外的错误,这一点至关重要.
- 让我们保留这个数字,因此转换为字符串或使用非数学技巧的函数并不理想.该程序将由一位数学家审核,他希望能够证明该函数完成了它应该做的事情.
- 速度...我要比较很多数字,所以越快越好.
- 我有 numpy、scipy 和标准库.其他任何东西对我来说都很难得到,尤其是对于项目的这么小部分.
解决方案
numpy.testing
中有一个函数assert_approx_equal
(来源这里)这可能是一个很好的起点.
There is a function assert_approx_equal
in numpy.testing
(source here) which may be a good starting point.
def assert_approx_equal(actual,desired,significant=7,err_msg='',verbose=True):
"""
Raise an assertion if two items are not equal up to significant digits.
.. note:: It is recommended to use one of `assert_allclose`,
`assert_array_almost_equal_nulp` or `assert_array_max_ulp`
instead of this function for more consistent floating point
comparisons.
Given two numbers, check that they are approximately equal.
Approximately equal is defined as the number of significant digits
that agree.
相关文章