Sort an array in place according to a given index

There are several questions that are close, but I have not found a specific answer to this question. I am trying to do some sort of local sorting of a massive 3D array along a given axis. I don't want a simple sort, though, I want to resort to an array according to my own index. for example

a = np.random.rand((3,3,3))


and let's say that I want to apply the last dimension according to the following indices of the old array:

new_order = [1,2,0]


I expect to be able to say:

a[:,:,new_order] = a


but this is not as expected. Suggestions?


source to share

2 answers


is the only type that claims to be in place and doesn't give you much control.

Placing the order index on the right works but can give unpredictable results. Obviously it does some sort of sequential assignment, and an earlier assignment on the left may affect the values ​​on the right.

In [719]: a=np.arange(12).reshape(3,4)
In [720]: a[:,[0,1,3,2]]=a
In [721]: a
array([[ 0,  1,  2,  2],
       [ 4,  5,  6,  6],
       [ 8,  9, 10, 10]])


Some buffering is predictably required to perform this kind of assignment.

In [728]: a[:,[0,1,3,2]]=a.copy()
In [729]: a
array([[ 0,  1,  3,  2],
       [ 4,  5,  7,  6],
       [ 8,  9, 11, 10]])


Indexing right turns around this, but it's out of place. The variable a

points to the new object.

In [731]: a=a[:,[0,1,3,2]]
In [732]: a
array([[ 0,  1,  3,  2],
       [ 4,  5,  7,  6],
       [ 8,  9, 11, 10]])


However, assigning with help [:]

might solve the following:

In [738]: a=np.arange(12).reshape(3,4)
In [739]: a.__array_interface__
{'data': (181868592, False),   # 181... is the id of the data buffer
 'descr': [('', '<i4')],
 'shape': (3, 4),
 'strides': None,
 'typestr': '<i4',
 'version': 3}
In [740]: a[:]=a[:,[0,1,3,2]]
In [741]: a.__array_interface__
{'data': (181868592, False),  # same data buffer
 'descr': [('', '<i4')],
 'shape': (3, 4),
 'strides': None,
 'typestr': '<i4',
 'version': 3}
In [742]: a
array([[ 0,  1,  3,  2],
       [ 4,  5,  7,  6],
       [ 8,  9, 11, 10]])


The fact that the id is

the same indicates that this is an inplace action. But it would be nice to test this with other indexers to make sure it does what you want.

But is the 'inplace' sort necessary? If the array is very large, you may need it to avoid memory errors. But we need to test the alternatives to see if they work.


matters if there is another variable that uses the same data. for example

b = a.T # a transpose


The a[:]=

lines b

will be reordered. a

and b

continue to share the same data

. C a=

, b

does not change. a

and are b

now untied.



Here you,

a = a[:, :, new_order]


Also, here are a couple of "numpy for Matlab user pages" that I found helpful when I started:



All Articles