Warning: file_get_contents(/data/phpspider/zhask/data//catemap/2/python/316.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Python 通过列表理解或映射加快numpy数组分配?_Python_Python 3.x_Multidimensional Array_Mapping_List Comprehension - Fatal编程技术网

Python 通过列表理解或映射加快numpy数组分配?

Python 通过列表理解或映射加快numpy数组分配?,python,python-3.x,multidimensional-array,mapping,list-comprehension,Python,Python 3.x,Multidimensional Array,Mapping,List Comprehension,我试图将一个小的2D numpy数组(“源”)的值添加到一个较大的2D numpy数组(“帧”)中,从帧数组中的特定位置(“pos_x”、“pos_y”)开始。现在,我有两个for循环,在每个位置将源值添加到帧值: for i in range(x): for j in range(y): frame[pos_x+i][pos_y+j] += source[i][j] (“x”和“y”是源阵列的形状) 但是,阵列相当大(帧阵列形状:5000x8000,源阵列形状:100

我试图将一个小的2D numpy数组(“源”)的值添加到一个较大的2D numpy数组(“帧”)中,从帧数组中的特定位置(“pos_x”、“pos_y”)开始。现在,我有两个for循环,在每个位置将源值添加到帧值:

for i in range(x):
    for j in range(y):
        frame[pos_x+i][pos_y+j] += source[i][j]
(“x”和“y”是源阵列的形状)

但是,阵列相当大(帧阵列形状:5000x8000,源阵列形状:1000x5000)。所以这个过程需要相当长的时间(约15秒)

有没有办法加快这个过程,通过列表理解、映射或其他方式

我尝试过通过多种语句和作业来理解列表:

frame = [[frame[pos_x+i][pos_y+j] + source[i][j] for j in range(y)] for i in range(x)]
(改编自螺纹:和)

但循环所需的时间与原始循环所需的时间一样长


另一个想法是,如果source[i][j]!=0。但是当我试着这么做的时候,花了三倍多的时间(潜在的子问题:知道为什么吗?)

切片在
numpy
中是可变的;因此,您可以执行以下操作:

import numpy as np

A = np.zeros((10,10), int)
B = np.zeros((5,5), int) + 5

A[2:7,2:7] += B

print(A)

您可以在这里利用numpy矢量化,而不是循环以获得巨大的加速。这只是计算指数和检查是否超出范围的问题

height, width = source.shape
pos_x2 = pos_x + width
pos_y2 = pos_y + height
#check for possible index out of range
fheight, fwidth = frame.shape
if pos_x2 > fwidth or pos_y2 > fheight:
    print('source out of frame bounds')
else:
    #add `source` to our slice of `frame`
    frame[pos_y:pos_y2, pos_x:pos_x2] += source

虽然从技术上讲,这将具有相同的时间复杂性,但numpy使用高效的编译C代码,可以利用硬件矢量化等功能,并且没有python解释器的所有开销。

我认为您发布的代码中有一个输入错误,在第二个代码块中,第二个范围应该是
range(x)
而不是
范围(xs)
,对吗?是的,谢谢(那些是我在更大程序中的旧变量名)。非常感谢!现在效果好多了!你知道有没有什么书、网站或其他东西可以让我通过这样的方式来学习优化代码(特别是关于内存分配、用c扩展等等)?@YohanneSaurus你永远不必像numpy(以及其他类似的库)那样明确地担心内存分配或类似的问题我会帮你处理的。Python经常因为速度慢而名声不佳,因为它有很多开销。您可以编写速度相当快的代码,但有时需要了解引擎盖下实际发生的事情,才能理解为什么有些事情比其他事情慢。我没有“银弹”教程或书,但我通常从不担心只运行一次的代码,但如果有大循环(或嵌套循环),我会尝试找到更快的库。