浮点运算错误 [英] Floating Point Arithmetic error
问题描述
我正在使用以下函数近似一个函数的派生:
I'm using the following function to approximate the derivative of a function at a point:
def prime_x(f, x, h):
if not f(x+h) == f(x) and not h == 0.0:
return (f(x+h) - f(x)) / h
else:
raise PrecisionError
作为一个测试,作为 f
作为 f
, x
其中 fx
是:
As a test I'm passing f
as fx
and x
as 3.0. Where fx
is:
def fx(x):
import math
return math.exp(x)*math.sin(x)
$ b $其中 exp(x)*(sin(x)+ cos(x))
作为导数。现在,根据Google和我的计算器
Which has exp(x)*(sin(x)+cos(x))
as derivative. Now, according to Google and to my calculator
exp(3)*(sin(3)+ cos(3))= -17.050059
。
到目前为止这么好。但是当我决定使用 h
的小值测试功能时,我得到以下内容:
So far so good. But when I decided to test the function with small values for h
I got the following:
print prime_x(fx, 3.0, 10**-5)
-17.0502585578
print prime_x(fx, 3.0, 10**-10)
-17.0500591423
print prime_x(fx, 3.0, 10**-12)
-17.0512493014
print prime_x(fx, 3.0, 10**-13)
-17.0352620898
print prime_x(fx, 3.0, 10**-16)
__main__.PrecisionError: Mantissa is 16 digits
为什么当h降低(某一点之后)误差增加?我期待相反,直到 f(x + h)
等于 f(x)
。
Why does the error increase when h decreases (after a certain point)? I was expecting the contrary until f(x+h)
was equal to f(x)
.
推荐答案
浮点算术(和整数运算和定点运算)具有一定的粒度:值只能以某一步长变化。对于IEEE-754 64位二进制格式,该步长大约为值(约2.22•10 -16 )的大约2 -52。对于物理测量来说,这非常小。
Floating-point arithmetic (and integer arithmetic and fixed-point arithmetic) has a certain granularity: Values can only change by a certain step size. For IEEE-754 64-bit binary format, that step size is about 2–52 times the value (about 2.22•10–16). That is very small for physical measurements.
然而,当您使 h 非常小时,f( x )和f(x + h))与步长相比不是很大。差异只能是步长的整数倍。
However, when you make h very small, the difference between f(x) and f(x+h) is not very large compared to the step size. The difference can only be an integral multiple of the step size.
当导数为 d 时,f(x) 是关于 h • d 。即使您以浮点格式计算f( x )和f( x + h ),测量值他们的差异必须是步长大小的倍数,所以它必须是圆的( h ? d / em>)• s ,其中round( y )是 y 四舍五入到最接近的整数。显然,当你使 h 更小时, h ? d / s 更小,所以舍入它的效果一个整数相对较大。
When the derivative is d, the change in f(x) is about h•d. Even if you calculate f(x) and f(x+h) as well as possible in the floating-point format, the measured value of their difference must be a multiple of the step size s, so it must be round(h•d/s)•s, where round(y) is y rounded to the nearest integer. Clearly, as you make h smaller, h•d/s is smaller, so the effect of rounding it to an integer is relatively larger.
另一种观察方式是,对于给定的f(x ),有一定的计算f(x )周围值之间的误差量。当您使 h 更小时,f( x + h ) - f(x )变小,错误保持不变。因此,错误相对于 h 增加。
Another way of looking at this is that, for a given f(x), there is a certain amount of error in calculating values around f(x). As you make h smaller, f(x+h)–f(x) gets smaller, but the error stays the same. Therefore, the error increases relative to h.
这篇关于浮点运算错误的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!