使用numpy来操作纯python列表

时间:2013-12-25 18:26:02

标签: python list numpy

我在纯python中有几部分代码,如:

[final_ids.append(list_item[0]) for list_item in newNodesCoord]
for line in nodes:
    if line[0] not in final_ids:
        newNodesCoord.append([line[0], 0., 0., 0.])

for i,row in enumerate(deformedCoord):
    x,y,z,nx,ny=row 
    for j, line in enumerate(nodesL):
        nodeID,x2,y2,z2=line
        if x==x2 and y==y2 and z==z2:
           newNodesCoord.append([nodeID, nx, ny, 0.])

然而,随着列表的大小增加代码检测器的性能。使用numpy有更快的方法吗? 谢谢!

1 个答案:

答案 0 :(得分:5)

NumPy数组不是最好的数据结构。 当你可以在一个漂亮的大数组上调用NumPy函数时,NumPy数组会闪耀(性能方面)。当你需要逐项遍历数组或逐行遍历数组时,它们并不是特别好。这就是你在代码中所做的事情。


以下是其他一些建议:

该行

line[0] not in final_ids:

可以通过final_ids set而不是list来加速。 Testing membership in a set is O(1),而在列表中测试成员资格为O(n)


同样,将nodesL dict映射到(x,y,z)nodeID值。然后你可以使用:

for x, y, z, nx, ny in deformedCoord:
    if (x,y,z) in nodesL:
        nodeID = nodesL[x,y,z]
        newNodesCoord.append([nodeID, nx, ny, 0.])  

如果每个(x,y,z)都有多个nodeID添加:

for nid in nodeID:
    newNodesCoord.append([nid, nx, ny, 0.])

newNodesCoord.extend([[nid, nx, ny, 0.] for nid in nodeID])

您的双for-loop时间复杂度为O(n*m),其中n = len(deformedCoord)m = len(nodesL)。如果您将nodesL设为dict,则if (x,y,z) in nodesLO(1),因此上述循环将在O(n)时间内运行。