Warning: file_get_contents(/data/phpspider/zhask/data//catemap/3/arrays/13.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 np.meshgrid的循环计算是否可以矢量化?_Python_Arrays_Performance_For Loop_Vectorization - Fatal编程技术网

Python np.meshgrid的循环计算是否可以矢量化?

Python np.meshgrid的循环计算是否可以矢量化?,python,arrays,performance,for-loop,vectorization,Python,Arrays,Performance,For Loop,Vectorization,我的代码中有一个部分,通过for循环,我将np.meshgrid应用于my_数组切片的结果分配到占位符res_数组,如下所示: p = 360; q = 50; r = 50 my_array = np.random.rand(p, q, 2) res_array = np.zeros((p,q,r), dtype=np.float32) for i in range(p): x, x_ = np.meshgrid(my_array[i,:,0], my_array[i,:,0])

我的代码中有一个部分,通过
for
循环,我将
np.meshgrid
应用于
my_数组
切片的结果分配到占位符
res_数组
,如下所示:

p = 360; q = 50; r = 50
my_array   =  np.random.rand(p, q, 2)
res_array  = np.zeros((p,q,r), dtype=np.float32)
for i in range(p):
   x, x_ = np.meshgrid(my_array[i,:,0], my_array[i,:,0])
   res_array[i] = (x_-x)
在我的代码中还有一些类似的操作,我必须运行代码几千次。因此,速度成为一个问题。我在想,如果我可以不使用
for
循环,我可以在这里节省一些时间,但是我自己无法做到

在没有for循环的情况下,如何实现这一点

编辑历史记录:


  • 请注意,
    my_数组[i,:,1]
    不用于上述snipet中。类似地,在另一个代码块中使用
    my_数组[I,:,1]
    (此处未显示,但类似循环)。这就是我所说的“在我的代码中还有一些类似的操作…”
  • 您可以这样做:

    my_array=np.random.rand(p,q,2)
    res_array=np.array([x[1]-x[0]表示[np.meshgrid(my_array[i,:,0],my_array[i,:,0])表示范围(p)]中的i,np.float32)。重塑(p,q,r)
    

    但是需要的时间比您多。

    您可以将np.meshgrid重写为更快的低级numpy操作:

    p=360;q=50;r=50
    my_array=np.random.rand(p,q,2)
    res_数组=np.zeros((p,q,r),dtype=np.float32)
    对于范围(p)内的i:
    x=my_数组[None,i,:,0]。重复(q,轴=0)。重塑(q,q)
    y=my_数组[None,i,:,0]。重复(q,轴=1)。重塑(q,q)
    res_数组[i]=y-x
    
    这个代码在我的机器上快了2倍。 Numba的
    @njit
    可以用来加速上述代码(同样快3倍),但使用它可以实现更高效的实现。这是:

    @njit(parallel=True)
    def fasterImpl(我的_数组,p,q,r):
    res_数组=np.zeros((p,q,r))
    对于prange中的i(p):
    对于范围(q)内的j:
    对于范围(r)内的k:
    res_数组[i,j,k]=my_数组[i,j,0]-my_数组[i,k,0]
    返回res_数组
    p=360;q=50;r=50
    my_array=np.random.rand(p,q,2)
    res_数组=fasterImpl(我的数组,p,q,r)
    

    这个最终的实现比我机器上最初的实现快29倍

    谢谢你。是的,我尝试了这个,但确实需要更长的时间。
    我的_数组[I,:,1]
    没有使用。这正常吗?你的意思是像
    np.meshgrid(我的数组[i,:,0],我的数组[i,:,1])
    ?谢谢你指出我们的@Jerome。类似地,我在另一个代码块中使用
    my_数组[I,:,1]
    。这就是我所说的“在我的代码中还有一些类似的操作……”1/2@Jerome。谢谢你和我分享你的知识。与500次函数运行的基准测试相比,您的第一个实现已经为我提供了约5秒的速度优势。这对我很有帮助。2/2然而,当我尝试
    Numba
    实现时,它给了我一个错误“类型数组的未知属性“repeat”。对不起,我以前没有用过
    Numba
    。我知道你今天在这个问题上帮助了我。在那里,虽然我可以让代码运行,但没有任何明显的速度提升。我怀疑我是否正确使用了它。现在,我已经将基于
    Numba
    的函数放在计算器函数之外,然后调用它。@your_boy_gorja我编辑了关于您的编辑的代码,以便可以轻松编辑代码。新的numba实现不再使用
    repeat
    (问题可能与numba版本有关)。新的numba代码甚至更快。关于numba版本的计时,请注意第一次运行通常比较慢,因为numba必须编译它。您应该多次使用它,这样它才有用(您也可以在程序开始时调用该函数,以便在任何热路径之外对其进行编译)。此外,在您的机器上,
    parallel=True
    +
    prange
    可能速度较慢(请在没有测试的情况下进行测试)。