Python Numpy阵列的真除法问题
假设您有以下数组:Python Numpy阵列的真除法问题,python,arrays,numpy,division,Python,Arrays,Numpy,Division,假设您有以下数组: In [29]: a = array([[10, 20, 30, 40, 50], [14, 28, 42, 56, 70], [18, 36, 54, 72, 90]]) Out[30]: a array([[ 0, 0, 0, 0, 0], [14, 28, 42, 56, 70], [18, 36, 54, 72, 90]]) 现在将第三行除以第一行(使用fromfutureimport division) 现在对循环中的每一行执
In [29]: a = array([[10, 20, 30, 40, 50], [14, 28, 42, 56, 70], [18, 36, 54, 72, 90]])
Out[30]: a
array([[ 0, 0, 0, 0, 0],
[14, 28, 42, 56, 70],
[18, 36, 54, 72, 90]])
现在将第三行除以第一行(使用fromfutureimport division)
现在对循环中的每一行执行相同的操作:
In [33]: for i in range(3):
print a[i]/a[2]
[ 0.55555556 0.55555556 0.55555556 0.55555556 0.55555556]
[ 0.77777778 0.77777778 0.77777778 0.77777778 0.77777778]
[ 1. 1. 1. 1. 1.]
一切看起来都很好。但是现在,将第一个数组a[i]/a[2]分配给a[i]:
In [35]: for i in range(3):
a[i]/=a[2]
....:
In [36]: a
Out[36]:
array([[0, 0, 0, 0, 0],
[0, 0, 0, 0, 0],
[1, 1, 1, 1, 1]])
好的,没问题。结果是。相反,我们应该:
In [38]: for i in range(3):
a[i] = a[i]/a[2]
....:
In [39]: a
Out[39]:
array([[0, 0, 0, 0, 0],
[0, 0, 0, 0, 0],
[1, 1, 1, 1, 1]])
但这不起作用。为什么以及如何修复它
提前感谢。您可以先将整个数组强制转换为
浮点数组:
a = a.astype('float')
a /= a[2]
“为什么不起作用”--它不起作用的原因是numpy数组在创建时有一个数据类型。任何将不同类型放入该数组的尝试都将转换为相应的类型。换句话说,当您尝试将浮点值放入整数数组时,numpy会将浮点值强制转换为int。这背后的原因是,numpy数组被设计为同伦类型,以便具有最佳性能。换句话说,它们在C中实现为数组。在C中,不能有一个数组,其中1个元素是float
,下一个元素是int
。(您可以使用类似的struct
s,但它们不是数组)
另一种解决方案(除了@nneonneo提出的方案外)是从一开始就将数组指定为浮点数组:
a = array([[10, 20, 30, 40, 50], [14, 28, 42, 56, 70], [18, 36, 54, 72, 90]], dtype=float)
问题不在于分工,而在于分配,即a[i]=…
(在执行a/=…
时也会在幕后使用)。试试这个:
>>> a = np.zeros(3, dtype='uint8')
>>> a[:] = [2, -3, 5.9]
>>> print a
[ 2 253 5]
当您执行intarray[i]=floatarray[i]
numpy操作时,必须截断浮点值以使其适合intarray
谢谢。是的,我考虑过这一点,但我想知道一个涉及除法的解决方案,因为它应该作为a[I]=a[I]/a[2]工作。如果不明显,这将创建一个新数组。据我所知,没有办法在适当的位置修改旧数组并更改类型。一般来说,这是不可能的,因为新旧类型可能有不同的大小,或者旧数组可能是不应该修改的其他数组的视图。@nneonneo--true--sort。从pythonapi的角度来看,这并不重要ndarray
是c数组(数据)的包装器。原则上,您可以将ndarray的指针移动到一个新的数据块,从python的角度来看,您可以“就地”执行操作。e、 g.a=数组(…);b=a;a、 魔术型转换(浮点);b、 dtype是a.dtype#true
。但是,我不知道这个行动是否存在。如果视图
包含对数据的相同引用(我认为是的),这也会起作用。@mgilson实际上,我没有考虑到这一点。然而,numpy数组仍然是可变的c=array([1]);id(c)返回32610992。然后c[0]=2将数组更改为array([2]),id(c)仍然返回32610992,所以我认为它可以按row.Right执行相同的操作。是的,您完全正确,因为.dtype返回dtype('int64'),那么一旦创建了一个数组,除非显式更改,否则它将保留其数据类型。是这样吗?@RobertSmith——不管发生什么,它都保持它的数据类型。不能显式更改数据类型。执行a.astype(float)
实际上创建了一个类型为float
的新数据数组。
>>> a = np.zeros(3, dtype='uint8')
>>> a[:] = [2, -3, 5.9]
>>> print a
[ 2 253 5]