我有两个列表,如下所示:
a= [[1,2,3,4], [2,3,4,5],[3,4,5,6,7]], b= [[5,6,7,8], [9,1,2,3], [4,5,6,7,8]]
我希望逐个元素地逐个减去输出,如下所示:
a-b= [[-4,-4,-4,-4],[7,2,2,2],[-1,-1,-1,-1,-1]]
为了做到这一点,我将每个a
和b
转换为数组并减去我使用的数据:
np.array(a)-np.array(b)
输出只是给我错误:
不支持的操作数类型 - :'list'和'list'
我做错了什么? np.array
命令不应该确保转换到数组吗?
答案 0 :(得分:5)
这是一种Numpythonic方式:
>>> y = map(len, a)
>>> a = np.hstack(np.array(a))
>>> b = np.hstack(np.array(b))
>>> np.split(a-b, np.cumsum(y))
[array([-4, -4, -4, -4]), array([-7, 2, 2, 2]), array([-1, -1, -1, -1, -1]), array([], dtype=float64)]
>>>
由于您无法减去具有不同形状的数组,因此可以使用np.hstack()
展平数组,然后减去展平的数组,然后根据以前的形状重新整形。
答案 1 :(得分:1)
两个数组的维度不匹配,即a
的前两个子列表有4个元素,但第三个有5个,而b
同上。如果您将列表转换为numpy arrays
,numpy
会默默地为您提供以下内容:
In [346]: aa = np.array(a)
In [347]: bb = np.array(b)
In [348]: aa
Out[348]: array([[1, 2, 3, 4], [2, 3, 4, 5], [3, 4, 5, 6, 7]], dtype=object)
In [349]: bb
Out[349]: array([[5, 6, 7, 8], [9, 1, 2, 3], [4, 5, 6, 7, 8]], dtype=object)
您需要确保所有子列表具有相同数量的元素,然后您的代码才能正常工作:
In [350]: a = [[1,2,3,4], [2,3,4,5],[3,4,5,6]]; b = [[5,6,7,8], [9,1,2,3], [4,5,6,7]] # I removed the last element of third sublist in a and b
In [351]: np.array(a) - np.array(b)
Out[351]:
array([[-4, -4, -4, -4],
[-7, 2, 2, 2],
[-1, -1, -1, -1]])
答案 2 :(得分:1)
您可以尝试:
>>> a= [[1,2,3,4], [2,3,4,5],[3,4,5,6,7]]
>>> b= [[5,6,7,8], [9,1,2,3], [4,5,6,7,8]]
>>>
>>> c =[]
>>> for i in range(len(a)):
c.append([A - B for A, B in zip(a[i], b[i])])
>>> print c
[[-4, -4, -4, -4], [-7, 2, 2, 2], [-1, -1, -1, -1, -1]]
或者 第二种方法是使用地图:
from operator import sub
a= [[1,2,3,4], [2,3,4,5],[3,4,5,6,7]]
b= [[5,6,7,8], [9,1,2,3], [4,5,6,7,8]]
c =[]
for i in range(len(a)):
c.append(map(sub, a[i], b[i]))
print c
[[-4, -4, -4, -4], [-7, 2, 2, 2], [-1, -1, -1, -1, -1]]
答案 3 :(得分:0)
没有NumPy:
result = []
for (m, n) in (zip(a, b)):
result.append([i - j for i, j in zip(m, n)])
另请参阅this question和this one。
答案 4 :(得分:0)
自定义函数怎么样,例如:
import numpy as np
a = [[1, 2, 3, 4], [2, 3, 4, 5], [3, 4, 5, 6, 7]]
b = [[5, 6, 7, 8], [9, 1, 2, 3], [4, 5, 6, 7, 8]]
def np_substract(l1, l2):
return np.array([np.array(l1[i]) - np.array(l2[i]) for i in range(len(l1))])
print np_substract(a, b)
答案 5 :(得分:0)
您收到错误,因为您的代码试图从子列表中减去子列表,如果您想使其工作,您可以通过以下方式执行相同的操作:
import numpy as np
a= [[1,2,3,4], [2,3,4,5],[3,4,5,6,7]]
b= [[5,6,7,8], [9,1,2,3], [4,5,6,7,8]]
#You can apply different condition here, like (if (len(a) == len(b)), then only run the following code
for each in range(len(a)):
list = np.array(a[each])-np.array(b[each])
#for converting the output array in to list
subList[each] = list.tolist()
print subList
答案 6 :(得分:0)
嵌套列表理解将完成这项工作:
In [102]: [[i2-j2 for i2,j2 in zip(i1,j1)] for i1,j1 in zip(a,b)]
Out[102]: [[-4, -4, -4, -4], [-7, 2, 2, 2], [-1, -1, -1, -1, -1]]
np.array(a)-np.array(b)
的问题是子列表的长度不同,因此生成的数组是对象类型 - 列表数组
In [104]: np.array(a)
Out[104]: array([[1, 2, 3, 4], [2, 3, 4, 5], [3, 4, 5, 6, 7]], dtype=object)
减法迭代外部数组就好了,但是当从另一个子列表中减去一个子列表时遇到问题 - 因此出现错误消息。
如果我创建了数组的输入数组,则减法将起作用
In [106]: np.array([np.array(a1) for a1 in a])
Out[106]: array([array([1, 2, 3, 4]), array([2, 3, 4, 5]), array([3, 4, 5, 6, 7])], dtype=object)
In [107]: aa=np.array([np.array(a1) for a1 in a])
In [108]: bb=np.array([np.array(a1) for a1 in b])
In [109]: aa-bb
Out[109]:
array([array([-4, -4, -4, -4]),
array([-7, 2, 2, 2]),
array([-1, -1, -1, -1, -1])], dtype=object)
您无法计算处理对象dtype数组的数组操作。但在这种情况下,subtraction
是为子数组定义的,因此它可以处理嵌套。
另一种进行嵌套的方法是使用np.subtract
。这是ufunc
-
版本,并会根据需要将np.asarray
应用于其输入:
In [103]: [np.subtract(i1,j1) for i1,j1 in zip(a,b)]
Out[103]: [array([-4, -4, -4, -4]), array([-7, 2, 2, 2]), array([-1, -1, -1, -1, -1])]
请注意,这些数组计算会返回数组或数组列表。将内部数组转回列表需要迭代。
如果您从列表开始,转换为数组通常不会节省时间。数组计算可以更快,但这并不能弥补首先创建数组的开销。
如果我将输入填充到相等长度,则简单数组减法有效,创建一个二维数组。
In [116]: ao= [[1,2,3,4,0], [2,3,4,5,0],[3,4,5,6,7]]; bo= [[5,6,7,8,0], [9,1,2,3,0], [4,5,6,7,8]]
In [117]: np.array(ao)-np.array(bo)
Out[117]:
array([[-4, -4, -4, -4, 0],
[-7, 2, 2, 2, 0],
[-1, -1, -1, -1, -1]])