我怎样才能向量化numpy的阵列的2×2子阵列的平均? [英] How can I vectorize the averaging of 2x2 sub-arrays of numpy array?

查看:128
本文介绍了我怎样才能向量化numpy的阵列的2×2子阵列的平均?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

我有一个包含了我需要的平均2x2的子集一个非常非常大的2D numpy的数组。我正在寻找一种方式来向量化此操作。例如,给定的x

I have a very a very large 2D numpy array that contains 2x2 subsets that I need to take the average of. I am looking for a way to vectorize this operation. For example, given x:

#               |- col 0 -|   |- col 1 -|   |- col 2 -|       
x = np.array( [[ 0.0,   1.0,   2.0,   3.0,   4.0,   5.0],  # row 0
               [ 6.0,   7.0,   8.0,   9.0,  10.0,  11.0],  # row 0
               [12.0,  13.0,  14.0,  15.0,  16.0,  17.0],  # row 1
               [18.0,  19.0,  20.0,  21.0,  22.0,  23.0]]) # row 1

我需要用的2x3阵列均为2×2子阵的平均值,即到结束:

I need to end up with a 2x3 array which are the averages of each 2x2 sub array, i.e.:

result = np.array( [[ 3.5,  5.5,  7.5],
                    [15.5, 17.5, 19.5]])

所以元素[0,0]被作为是x计算[0:2,0:2],而元件[0,1]是x的平均值[2:4,0:2]。是否numpy的已矢量/关于高效亚聚集做这样的方式?

so element [0,0] is calculated as the average of x[0:2,0:2], while element [0,1] would be the average of x[2:4, 0:2]. Does numpy have vectorized/efficient ways of doing aggregates on subsets like this?

推荐答案

如果我们形成重构矩阵 Y = x.reshape(2,2,3,2) ,那么第(i,j)的2×2子矩阵是由给Y [我,:,J:] 。例如:

If we form the reshaped matrix y = x.reshape(2,2,3,2), then the (i,j) 2x2 submatrix is given by y[i,:,j,:]. E.g.:

In [340]: x
Out[340]: 
array([[  0.,   1.,   2.,   3.,   4.,   5.],
       [  6.,   7.,   8.,   9.,  10.,  11.],
       [ 12.,  13.,  14.,  15.,  16.,  17.],
       [ 18.,  19.,  20.,  21.,  22.,  23.]])

In [341]: y = x.reshape(2,2,3,2)

In [342]: y[0,:,0,:]
Out[342]: 
array([[ 0.,  1.],
       [ 6.,  7.]])

In [343]: y[1,:,2,:]
Out[343]: 
array([[ 16.,  17.],
       [ 22.,  23.]])

要获得2×2子矩阵的平均值,使用的意思是法,用轴=(1,3)

To get the mean of the 2x2 submatrices, use the mean method, with axis=(1,3):

In [344]: y.mean(axis=(1,3))
Out[344]: 
array([[  3.5,   5.5,   7.5],
       [ 15.5,  17.5,  19.5]])

如果您使用numpy的一个旧版本,不使用一个元组为中轴线的支持,你可以这样做:

If you are using an older version of numpy that doesn't support using a tuple for the axis, you could do:

In [345]: y.mean(axis=1).mean(axis=-1)
Out[345]: 
array([[  3.5,   5.5,   7.5],
       [ 15.5,  17.5,  19.5]])

查看评论由@dashesy给出的链接,对整形猫腻更多的背景。

See the link given by @dashesy in a comment for more background on the reshaping "trick".

要与形状(M,N),推广为一个二维数组,其中m和n是偶数,用

To generalize this to a 2-d array with shape (m, n), where m and n are even, use

y = x.reshape(x.shape[0]/2, 2, x.shape[1], 2)

则可以PTED为2×2数组的数组间$ P $。在4-D阵列充当该选择的2×2块中的一个的索引的第一和第三索引时隙。为了得到左上的2x2块,使用 Y [0:0,:] ;到块的第二行和第三列中的块中,使用 Y [1,:,2,:] ;在一般情况下,存取权限块(J,K),使用ÿ[J,:,K:]

y can then be interpreted as an array of 2x2 arrays. The first and third index slots of the 4-d array act as the indices that select one of the 2x2 blocks. To get the upper left 2x2 block, use y[0, :, 0, :]; to the block in the second row and third column of blocks, use y[1, :, 2, :]; and in general, to acces block (j, k), use y[j, :, k, :].

要计算这些块的平均值的降低阵列,使用的意思是法,用轴=(1,3)(即平均值轴1和3):

To compute the reduced array of averages of these blocks, use the mean method, with axis=(1, 3) (i.e. average over axes 1 and 3):

avg = y.mean(axis=(1, 3))

下面是一个例子,其中 X 具有形状(8,10),因此2×2块的平均值的阵列具有形状(4,5):

Here's an example where x has shape (8, 10), so the array of averages of the 2x2 blocks has shape (4, 5):

In [10]: np.random.seed(123)

In [11]: x = np.random.randint(0, 4, size=(8, 10))

In [12]: x
Out[12]: 
array([[2, 1, 2, 2, 0, 2, 2, 1, 3, 2],
       [3, 1, 2, 1, 0, 1, 2, 3, 1, 0],
       [2, 0, 3, 1, 3, 2, 1, 0, 0, 0],
       [0, 1, 3, 3, 2, 0, 3, 2, 0, 3],
       [0, 1, 0, 3, 1, 3, 0, 0, 0, 2],
       [1, 1, 2, 2, 3, 2, 1, 0, 0, 3],
       [2, 1, 0, 3, 2, 2, 2, 2, 1, 2],
       [0, 3, 3, 3, 1, 0, 2, 0, 2, 1]])

In [13]: y = x.reshape(x.shape[0]/2, 2, x.shape[1]/2, 2)

一对夫妇的2×2块看看:

Take a look at a couple of the 2x2 blocks:

In [14]: y[0, :, 0, :]
Out[14]: 
array([[2, 1],
       [3, 1]])

In [15]: y[1, :, 2, :]
Out[15]: 
array([[3, 2],
       [2, 0]])

计算各块的平均值:

Compute the averages of the blocks:

In [16]: avg = y.mean(axis=(1, 3))

In [17]: avg
Out[17]: 
array([[ 1.75,  1.75,  0.75,  2.  ,  1.5 ],
       [ 0.75,  2.5 ,  1.75,  1.5 ,  0.75],
       [ 0.75,  1.75,  2.25,  0.25,  1.25],
       [ 1.5 ,  2.25,  1.25,  1.5 ,  1.5 ]])

这篇关于我怎样才能向量化numpy的阵列的2×2子阵列的平均?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆