2

由于我是 Numpy 新手,因此在实现我用 C++ 编写的特定代码时遇到了问题

for(i=0;i<h;i++)
{
    for(j=0;j<w;j++)
    {
        val=0;
        for(i1=-size;i1<=size;i1++)
        {
            for(j1=-size;j1<=size;j1++)
            {
                h1=i+i1,w1=j+j1;
                if (w1<=0) w1=w1+w;
                if (h1<=0) h1=h1+h;
                if (w1>=w) w1=w1-w;
                if (h1>=h) h1=h1-h;
                val=val+sqrt(pow(data[i][j][0]-data[h1][w1][0],2)
                            +pow(data[i][j][1]-data[h1][w1][1],2)
                            +pow(data[i][j][2]-data[h1][w1][2],2));
            }
        }
    }
}

如您所见,我基本上是为 [i,j] 元素添加欧几里得距离,其中每个元素都是子矩阵 [i-size to i+size][j-size to j+size] 的一部分

如何在 python 中编写代码,而不必使用循环对 numpy 数组中的每个元素执行一些操作,这些操作取决于其行和列位置。或者必须有某种优化它的方法。

这是我目前的实现,就像非常非常慢

for i in range(0,h):
    for j in range(0,w):
        for i1 in range(-window_size, window_size+1):
            for j1 in range(-window_size, window_size+1):
                h1=i+i1
                w1=j+j1
                if w1 <= 0:
                    w1+=w
                if  h1 <= 0:
                    h1+=h
                if w1 >= w:
                    w1-=w
                if h1 >= h:
                    h1-=h
                val[i][j] += np.sqrt(((source_pyr_down_3_Luv[i][j][0] - source_pyr_down_3_Luv[h1][w1][0])**2)
                                    +((source_pyr_down_3_Luv[i][j][1] - source_pyr_down_3_Luv[h1][w1][1])**2)
                                    +((source_pyr_down_3_Luv[i][j][2] - source_pyr_down_3_Luv[h1][w1][2])**2))

运行这段代码几乎花了 6 分钟。

4

2 回答 2

3

访问子数组 im numpy 尝试:

data[i-size:i+size,j-size:j+size]

编辑这个子数组(在这种情况下对每个元素简单 +1):

data[i-size:i+size,j-size:j+size] += 1

或获取另一个数组,其中包含 2 个数组(形状为 (n,2))的元素之间的距离:

data3 = np.sqrt(np.power(data1[:,0]-data2[:,0],2)+ np.power(data1[:,1]-data2[:,1],2))

我知道这不是一个完整的答案,但我希望它可以帮助您入门。

于 2012-12-26T22:30:29.143 回答
2

您可以通过预先扩展原始矩阵来避免显式内部循环并直接计算欧几里德距离矩阵,这样就不需要对元素索引进行检查:

# Extend the matrix to avoid modular access
h, w, _ = data.shape
exdata = numpy.zeros((h+2*size, w+2*size, 2), data.dtype)
exdata[size:-size, size:-size, :] = data[:,:,:]  # Fill central part
exdata[:size,:,:] = exdata[-size*2:-size,:,:]    # Copy last rows to begin
exdata[-size:,:,:] = exdata[size:size*2,:,:]     # Copy first rows to end
exdata[:,:size,:] = exdata[:,-size*2:-size,:]    # Copy last cols to begin
exdata[:,-size:,:] = exdata[:,size:size*2,:]     # Copy first cols to end

# Do the actual computation
val = 0
for i in xrange(h):
    for j in xrange(w):
        dx = numpy.copy(exdata[i:i+size*2+1, j:j+size*2+1, 0])  # all x values
        dy = numpy.copy(exdata[i:i+size*2+1, j:j+size*2+1, 1])  # all y values
        dx -= dx[size, size] # subtract central x
        dy -= dy[size, size] # subtract central y
        dx *= dx # square dx
        dy *= dy # square dy
        dx += dy # sum of squares
        val += numpy.sum(dx ** 0.5)
于 2012-12-26T22:58:50.683 回答