Aristotle0 - 1 year ago 79
Python Question

# How to evaluate the sum of values within array blocks

I have data array, with shape 100x100. I want to divide it into 5x5 blocks, and each block has 20x20 grids. The value of each block I want is the sum of all values in it.

Is there a more elegant way to accomplish it?

``````x = np.arange(100)
y = np.arange(100)
X, Y = np.meshgrid(x, y)
Z = np.cos(X)*np.sin(Y)
Z_new = np.zeros((5, 5))
for i in range(5):
for j in range(5):
Z_new[i, j] = np.sum(Z[i*20:20+i*20, j*20:20+j*20])
``````

This is based on index, how if based on x?

``````x = np.linspace(0, 1, 100)
y = np.linspace(0, 1, 100)
X, Y = np.meshgrid(x, y)
Z = np.cos(X)*np.sin(Y)
x_new = np.linspace(0, 1, 15)
y_new = np.linspace(0, 1, 15)
``````

Z_new?

Simply `reshape` splitting each of those two axes into two each with shape `(5,20)` and then sum reduce along the axes having the lengths `20`, like so -

``````Z_new = Z.reshape(5,20,5,20).sum(axis=(1,3))
``````

Functionally the same, but potentially faster option with `np.einsum` -

``````Z_new = np.einsum('ijkl->ik',Z.reshape(5,20,5,20))
``````

Runtime test -

``````In [18]: x = np.arange(100)
...: y = np.arange(100)
...: X, Y = np.meshgrid(x, y)
...: Z = np.cos(X)*np.sin(Y)
...:

In [19]: %timeit Z.reshape(5,20,5,20).sum(axis=(1,3))
10000 loops, best of 3: 49.5 µs per loop

In [20]: %timeit np.einsum('ijkl->ik',Z.reshape(5,20,5,20))
10000 loops, best of 3: 46.7 µs per loop
``````
Recommended from our users: Dynamic Network Monitoring from WhatsUp Gold from IPSwitch. Free Download