不同版本的Python 2.7和Numpy为同一个脚本生成不同的结果

时间:2016-03-03 20:49:11

标签: python-2.7 debugging numpy

我有以下脚本:

import numpy as np

pin_info = {}

pinID = 4 
pin_info[pinID] = {}
pin_info[pinID]['matvols'] = np.array([0.4096,0.418,0.475,1.26])**2
pin_info[pinID]['matvols'][:-1] *= np.pi
pin_info[pinID]['matvols'][1:] -= pin_info[pinID]['matvols'][:-1]
print(pin_info)

我的工作机器使用Python 2.7.3和Numpy 1.6.1,并给出以下结果:

{4: {'matvols': array([ 0.52707179,  0.02183985,  0.68698199,  0.90061801])}

我的本​​地机器使用Python 2.7.11和Numpy 1.10.4,并给出以下结果:

{4: {'matvols': array([ 0.52707179,  0.02183985,  0.68698199,  0.87877816])}}

除非我的数学不正确,否则本地机器产生的结果应该是正确答案。 (工作机器得到了pin_info [4] [' matvols']错误的最后一项。但是,我不知道为什么我的工作机器产生了错误的答案。有人有什么想法吗?我在两台机器上运行完全相同的脚本。我甚至对文件进行了测试,以确保它们完全相同。

编辑:如果您的Python / Numpy版本接近2.7.3 / 1.6.1,那么如果您可以尝试使用此脚本并查看获得的答案,那就太棒了。

1 个答案:

答案 0 :(得分:1)

~0.87877816确实是正确的结果:

  • 使用calc(来自 Ubuntu package apcalc):

    calc '1.26^2 - 0.475^2 * pi()'
    

            ~0.87877815753380290057
  • 使用NumPy:

    In [6]: np.dot(np.array([0.475, 1.26]) ** 2 * np.array([np.pi, 1]), np.array([-1, 1]))
    Out[6]: 0.87877815753380306
    

直到-=操作之前,一切都按预期工作:

In [1]: %cpaste
Pasting code; enter '--' alone on the line to stop or use Ctrl-D.
:import numpy as np
:
:pin_info = {}
:
:pinID = 4 
:pin_info[pinID] = {}
:pin_info[pinID]['matIDs'] = [1,4,5,6]
:pin_info[pinID]['matvols'] = np.array([0.4096,0.418,0.475,1.26])**2
:pin_info[pinID]['matvols'][:-1] *= np.pi
:--

In [2]: pin_info[pinID]['matvols']
Out[2]: array([ 0.52707179,  0.54891163,  0.70882184,  1.5876    ])

切片也有效:

In [3]: pin_info[pinID]['matvols'][1:]
Out[3]: array([ 0.54891163,  0.70882184,  1.5876    ])

In [4]: pin_info[pinID]['matvols'][:-1]
Out[4]: array([ 0.52707179,  0.54891163,  0.70882184])

实际上,我们可以从这里计算出正确的结果:

In [5]: pin_info[pinID]['matvols'][1:] - pin_info[pinID]['matvols'][:-1]
Out[5]: array([ 0.02183985,  0.15991021,  0.87877816])

但是-=似乎没有做正确的事情:

In [7]: pin_info[pinID]['matvols'][1:] -= pin_info[pinID]['matvols'][:-1]

In [8]: pin_info
Out[8]: 
{4: {'matIDs': [1, 4, 5, 6],
  'matvols': array([ 0.52707179,  0.02183985,  0.68698199,  0.90061801])}}

(使用Python 3.2.3和NumPy 1.6.1以及Python 2.7.3和(也)NumPy 1.6.1重现。)

那么这里发生了什么?让我们看一个整数示例:

In [1]: import numpy as np

In [2]: x = np.array([5, 23, 42, 1000])

In [3]: x[1:] - x[:-1]
Out[3]: array([ 18,  19, 958])

In [4]: x[1:] -= x[:-1]

In [5]: x
Out[5]: array([  5,  18,  24, 976])

你能看到这种模式吗?它从左到右处理组件,并使用已修改的值来计算后续组件。我们可以在没有NumPy的情况下模仿这个:

In [1]: x = [5, 23, 42, 1000]

In [2]: for i in range(len(x) - 1):
   ...:     x[i + 1] -= x[i]
   ...: 

In [3]: x
Out[3]: [5, 18, 24, 976]

我想这是/是NumPy 1.6中的一个错误,在以后的某个版本中得到修复。