我有一个简单的问题,对于Google来说真的很难(除了每位计算机科学家应该知道的有关浮点算术的规范论文之外)。
什么时候应该使用诸如log1p或的功能expm1代替log和exp?什么时候不应该使用它们?这些功能的不同实现在用法上有何不同?
我有一个简单的问题,对于Google来说真的很难(除了每位计算机科学家应该知道的有关浮点算术的规范论文之外)。
什么时候应该使用诸如log1p或的功能expm1代替log和exp?什么时候不应该使用它们?这些功能的不同实现在用法上有何不同?
Answers:
我们都知道,
这可以在python中轻松演示:
>>> from math import (exp, expm1)
>>> x = 1e-8
>>> exp(x) - 1
9.99999993922529e-09
>>> expm1(x)
1.0000000050000001e-08
>>> x = 1e-22
>>> exp(x) - 1
0.0
>>> expm1(x)
1e-22
精确值为
通常,“准确”的实现,exp并且expm1应正确不超过1ULP(即最后一个单元)。但是,由于达到此精度会导致代码“缓慢”,因此有时可以使用快速,精度较低的实现。例如在CUDA中,我们有expfand expm1f,其中f代表快速。根据CUDA C编程指南,app。D的expf错误为2ULP。
如果您不在乎几个ULPS顺序的错误,通常指数函数的不同实现是等效的,但是请注意,错误可能隐藏在某处...(还记得Pentium FDIV错误吗?)
所以这是很清楚,expm1应该被用来计算为小型。将其用于一般并无害处,因为expm1可以预期它在整个范围内都是准确的:
>>> exp(200)-1 == exp(200) == expm1(200)
True
(在上面的示例中远低于 1ULP ,因此所有三个表达式都返回完全相同的浮点数。)
类似的讨论适用于逆函数log和log1p自为。
expm1(x)代替exp(x)-1。当然exp(x) == exp(x) - 1一般不成立。
为了扩大两者之间的差异,如果对数log,log1p则可能有助于调出图形:
log is potentially a large negative number. For example and and so on. This can be useful, but it can also distort your data towards large negative numbers, especially if your dataset also contains numbers much larger than zero.
On the other hand, as approaches , the value of approaches from the positive direction. For example and . So log1p produces only positive values and removes the 'danger' of large negative numbers. This generally insures a more homogeneous distribution when a dataset contains numbers close to zero.
In short, if the dataset is all greater than , then log is usually fine. But, if the dataset has numbers between and , then log1p is usually better.
log1p你指的是(它尤其是如何实现的,所以我们不必去猜测)。