[英]Integer overflow in numpy arrays
import numpy as np
a = np.arange(1000000).reshape(1000,1000)
print(a**2)
有了这个代码,我得到了这个答案。 为什么我得到负值?
[[ 0 1 4 ..., 994009 996004 998001]
[ 1000000 1002001 1004004 ..., 3988009 3992004 3996001]
[ 4000000 4004001 4008004 ..., 8982009 8988004 8994001]
...,
[1871554624 1873548625 1875542628 ..., -434400663 -432404668 -430408671]
[-428412672 -426416671 -424420668 ..., 1562593337 1564591332 1566589329]
[1568587328 1570585329 1572583332 ..., -733379959 -731379964 -729379967]]
在您的平台上, np.arange 返回一个 dtype 'int32' 数组:
In [1]: np.arange(1000000).dtype
Out[1]: dtype('int32')
数组的每个元素都是一个 32 位整数。 平方导致不适合 32 位的结果。 结果被裁剪为 32 位,但仍被解释为 32 位整数,这就是您看到负数的原因。
编辑:在这种情况下,您可以通过在平方之前构造一个 dtype 'int64' 数组来避免整数溢出:
a=np.arange(1000000,dtype='int64').reshape(1000,1000)
请注意,您发现的问题是使用 numpy 时固有的危险。 您必须谨慎选择 dtype,并事先知道您的代码不会导致算术溢出。 为了速度,numpy 不能也不会在发生这种情况时发出警告。
请参阅http://mail.scipy.org/pipermail/numpy-discussion/2009-April/041691.html在 numpy 邮件列表上对此进行讨论。
python integers 没有这个问题,因为它们在溢出时会自动升级为 python long integers。
因此,如果您确实设法使 int64 溢出,一种解决方案是在 numpy 数组中使用 python int:
import numpy
a=numpy.arange(1000,dtype=object)
a**20
numpy 整数类型是固定宽度的,您会看到整数溢出的结果。
这个问题的解决方案如下(取自here ):
...在类 StringConverter._mapper (numpy/lib/_iotools.py) 中的更改来自:
{{{
_mapper = [(nx.bool_, str2bool, False),
(nx.integer, int, -1),
(nx.floating, float, nx.nan),
(complex, _bytes_to_complex, nx.nan + 0j),
(nx.string_, bytes, asbytes('???'))]
}}}
到
{{{
_mapper = [(nx.bool_, str2bool, False),
(nx.int64, int, -1),
(nx.floating, float, nx.nan),
(complex, _bytes_to_complex, nx.nan + 0j),
(nx.string_, bytes, asbytes('???'))]
}}}
这解决了我在numpy.genfromtxt
的类似问题
请注意,作者将其描述为“临时”和“非最佳”解决方案。 但是,我使用 v2.7 没有任何副作用(还有?!)。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.