[SciPy-User] autocrop 2d array

Zachary Pincus zachary.pincus at yale.edu
Thu May 12 12:42:13 EDT 2011


Here's what came to mind: grab the indices at which the array is nonzero, then calculate the bounding box from that. Not the most efficient (which you could do easily enough in a cython loop), but compact and pure-python.

Perhaps there's a better way, but this may suffice.

import numpy
a = numpy.zeros((10,10),int)
a[5,3:7] = 1; a[3:7,5] = 1
print a

array([[0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
       [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
       [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
       [0, 0, 0, 0, 0, 1, 0, 0, 0, 0],
       [0, 0, 0, 0, 0, 1, 0, 0, 0, 0],
       [0, 0, 0, 1, 1, 1, 1, 0, 0, 0],
       [0, 0, 0, 0, 0, 1, 0, 0, 0, 0],
       [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
       [0, 0, 0, 0, 0, 0, 0, 0, 0, 0],
       [0, 0, 0, 0, 0, 0, 0, 0, 0, 0]])

xs, ys = numpy.indices(a.shape)
xi, yi = xs[a!=0], ys[a!=0]
print a[xi.min():xi.max()+1, yi.min():yi.max()+1]

array([[0, 0, 1, 0],
       [0, 0, 1, 0],
       [1, 1, 1, 1],
       [0, 0, 1, 0]])




On May 12, 2011, at 11:56 AM, Christian K. wrote:

> Hi Zach,
> 
> Zachary Pincus <zachary.pincus <at> yale.edu> writes:
> 
>> 
>> If you can specify the problem a little more clearly (I'm not familiar with 
> autocrop) maybe I could help. Are
>> you looking for the smallest sub-array containing all of the non-zero values 
> in the array? (That is, to
>> trim off zero-valued borders?)
>> 
> 
> That is exactly what I want. In case the subarray has the same layout as the 
> containing array - square shape - it is equal to 
> 
> data[data != 0]
> 
> but I also need a subarray for the general case of arbitrarily shaped objects 
> within the array.
> 
> Regards, Christian
> 
> 
> 
> _______________________________________________
> SciPy-User mailing list
> SciPy-User at scipy.org
> http://mail.scipy.org/mailman/listinfo/scipy-user




More information about the SciPy-User mailing list