Python认为Euler有身份问题(cmath返回奇怪的结果)



我的代码:

import math
import cmath
print "E^ln(-1)", cmath.exp(cmath.log(-1))

打印内容:

E^ln(-1) (-1+1.2246467991473532E-16j)

打印内容:

-1

(供参考,谷歌检查我的计算)

根据python.org上的文档,cmath.exp(x)返回e^(x), cmath.log(x)返回ln (x),所以除非我缺少分号或其他东西,这是一个非常简单的三行程序。

当我测试cmath.log(-1)时,它返回π I (技术上是3.141592653589793j)。这是对的。欧拉恒等式说e^(πi) = -1,然而Python说当我取e^(πi)时,我会得到一些疯狂的对话(特别是-1+1.2246467991473532E-16j)。

为什么Python讨厌我,我该如何安抚它?

是否有一个库可以使它正确地进行数学运算,或者我必须向van Rossum做出牺牲?这是某种浮点精度问题吗?

我遇到的最大问题是,在最终函数(未显示)中,精度足以使其他值看起来更接近于0,而不是实际的零,因此布尔测试是毫无价值的(即if(x==0)),因此是局部最小值,等等…

例如,在下面的迭代中:

X = 2 Y= (-2-1.4708141202500006E-15j)
X = 3 Y= -2.449293598294706E-15j
X = 4 Y= -2.204364238465236E-15j
X = 5 Y= -2.204364238465236E-15j
X = 6 Y= (-2-6.123233995736765E-16j)
X = 7 Y= -2.449293598294706E-15j

3,7实际上都等于0,但它们似乎有最大的虚部,而4和5根本没有实部。

不好意思。非常沮丧。

正如您已经演示过的,cmath.log(-1)并不完全返回 i*pi。当然,完全返回pi是不可能的,因为pi是一个无理数…

现在你把e提高到不完全是i*pi的某个数的幂,你期望得到的正好是-1。然而,如果cmath返回,你会得到一个不正确的结果。(毕竟,exp(i*pi+epsilon)不应该等于-1——欧拉没有做出这样的声明!)。

无论如何,结果非常接近您所期望的——实数部分是-1,虚数部分接近浮点精度。

似乎是一个四舍五入的问题。虽然-1+1.22460635382e-16j不是一个正确的值,但1.22460635382e-16j非常接近于零。我不知道如何解决这个问题,但一个快速而肮脏的方法是将数字四舍五入到点后的特定位数(可能是14 ?).

小于10^-15的值通常为零。计算机计算有一定的误差,通常在这个范围内。浮点表示是表示,而不是精确值。

这个问题是将有限空间中的无理数(如π)表示为浮点数所固有的。

你能做的最好的是过滤你的结果,如果它的值在给定的范围内,把它设置为零。

>>> tolerance = 1e-15
>>> def clean_complex(c):
...   real,imag = c.real, c.imag
...   if -tolerance < real < tolerance:
...     real = 0
...   if -tolerance < imag < tolerance:
...     imag = 0
...   return complex(real,imag)
... 
>>> clean_complex( cmath.exp(cmath.log(-1)) )
(-1+0j)

最新更新