6

How do i "carve" or mask a 2D numpy array according to an index formula? I don't care what the element value is, only its position in the array.

For example, given an mxm array, how do I extract all elements whose address conforms to

for i in range(0,m):
    for j in range(0,m):
        if j-i-k>=0:
            A[i,j] = 1
        elif j-p-k>=0:
            A[i,j] = 1
        elif i-k>=0:
            A[i,j] = 1
        else:
            A[i,j] = 0
        j=j+1
    i=i+1

where

k and p are an arbitrary fences

Assume

k<m
p<m

This ends up looking like a diagonal slice + a horizontal slice + a vertical slice. Can it be done without the for loops above?

1
  • Further question on new_data = data[mask] @tcaswell, using my "for" created mask "removes" some rows and columns and somehow leaves me with a vector, not an array of the original data.shape. Why? How can I prevent this? Commented Nov 19, 2012 at 21:21

3 Answers 3

3
In [1]: import numpy as np

In [2]: k = 2

In [3]: i, j = np.ogrid[0:5,0:5]

In [4]: mask = (j-i-k < 0)

In [5]: mask
Out[5]: 
array([[ True,  True, False, False, False],
       [ True,  True,  True, False, False],
       [ True,  True,  True,  True, False],
       [ True,  True,  True,  True,  True],
       [ True,  True,  True,  True,  True]], dtype=bool)

In [6]: mask.shape
Out[6]: (5, 5)

In [7]: mask.dtype
Out[7]: dtype('bool')
Sign up to request clarification or add additional context in comments.

Comments

1
xdim,ydim = data.shape
k = 2
a, b = np.meshgrid(range(ydim),range(xdim))
mask = (b - a -k) < 0

new_data = data[mask]

new_data2 = np.array(data) # to force a copy
new_data2[~mask] = 0

new_data is a vector because the masking processes (done this way) flattens the array. Your are selecting a shape with a ragged that cannot be represented as an array. If you just want to set the non-selcted values to 0, use new_data2.

Comments

1

Here's yet another way using np.indices:

>>> import numpy as np
>>> a = np.arange(90).reshape(10,9)
>>> b = np.indices(a.shape)
>>> k = 2
>>> i = b[1] - b[0] - k
>>> a[i < 0]
array([ 0,  1,  9, 10, 11, 18, 19, 20, 21, 27, 28, 29, 30, 31, 36, 37, 38,
   39, 40, 41, 45, 46, 47, 48, 49, 50, 51, 54, 55, 56, 57, 58, 59, 60,
   61, 63, 64, 65, 66, 67, 68, 69, 70, 71, 72, 73, 74, 75, 76, 77, 78,
   79, 80, 81, 82, 83, 84, 85, 86, 87, 88, 89])

Comments

Your Answer

By clicking “Post Your Answer”, you agree to our terms of service and acknowledge you have read our privacy policy.

Start asking to get answers

Find the answer to your question by asking.

Ask question

Explore related questions

See similar questions with these tags.