[Numpy-discussion] summarizing blocks of an array using a moving window

Warren Weckesser warren.weckesser at enthought.com
Thu Jul 22 10:48:04 EDT 2010


Pauli Virtanen wrote:
> Thu, 22 Jul 2010 00:47:20 -0400, Robin Kraft wrote:
> [clip]
>   
>> Let's say the image looks like this: np.random.randint(0,2,
>> 16).reshape(4,4)
>>
>> array([[0, 0, 0, 1],
>>        [0, 0, 1, 1],
>>        [1, 1, 0, 0],
>>        [0, 0, 0, 0]])
>>
>> I want to use a square, non-overlapping moving window for resampling, so
>> that I get a count of all the 1's in each 2x2 window.
>>
>> 0, 0,   0, 1
>> 0, 0,   1, 1                 0  3
>>                     =>       2  0
>> 1, 1,   0, 0
>> 0, 0,   0, 0
>>
>> In another situation with similar data I'll need the average, or the
>> maximum value, etc..
>>     
>
> Non-overlapping windows can be done by reshaping:
>
> x = np.array([[0, 0, 0, 1, 1, 1],
>               [0, 0, 1, 1, 0, 0],
>               [1, 1, 0, 0, 1, 1],
>               [0, 0, 0, 0, 1, 1],
>               [1, 0, 1, 0, 1, 1],
>               [0, 0, 1, 0, 0, 0]])
>
> y = x.reshape(3,2,3,2)
> y2 = y.sum(axis=3).sum(axis=1)
>
> # -> array([[0, 3, 2],
> #           [2, 0, 4],
> #           [1, 2, 2]])
>
> y2 = x.reshape(3,2,3,2).transpose(0,2,1,3).reshape(3,3,4).sum(axis=-1)
>
> # -> array([[0, 3, 2],
> #           [2, 0, 4],
> #           [1, 2, 2]])
>
>
> The above requires no copying of data, and should be relatively fast.

Actually, because of the use of reshape(3,3,4), your second
example does make a copy.

Warren

>  If 
> you need overlapping windows, those can be emulated with strides:
>
> 	http://mentat.za.net/numpy/scipy2009/stefanv_numpy_advanced.pdf
> 	http://conference.scipy.org/scipy2010/slides/tutorials
> 	/stefan_vd_walt_numpy_advanced.pdf
>
>   




More information about the NumPy-Discussion mailing list