2

I have an array that I'm trying to sort. Some of the entries are strings and so numpy treats everything as strings (including numbers). On the whole this is fine and I actually take advantage of it in a few places, however when trying to sort it results in some problems.

Basically the problem comes when the string length is different (so if it's sorting say 50, 120, 110 it'll give 110, 120, 50 instead of 50, 110, 120).

Below is a simple example of what's going on; does anyone know how to overcome this problem (if I can keep the elements as strings post sorting that would be great, but I can make do if not).

import numpy as np


spam = np.array( [ [ 'Graham', 550, 29 ], [ 'John', 90, 1 ], [ 'Terry G', 450, 20 ], \
                   [ 'Eric', 550, 30   ], [ 'Terry J', 450, 20 ], [ 'Michael', 520, 33 ] ] )

print( "Original:\n")
print( spam )
print( "\n\nSorted:\n" )


spam = spam[ np.lexsort( ( spam[ :, 2 ], spam[ :, 1 ] ) ) ][ : : -1 ]

print( spam )

If any information is missing, etc. please don't hesitate to ask. As always, thanks in advance for the help & apologies if this is a duplicate (search returned no relevant results as far as I could see).

1 Answer 1

2

Convert to int type for lexsort and then use those lex-sorted indices to index into input array -

sidx = np.lexsort(( spam[ :, 2 ].astype(int), spam[ :, 1 ].astype(int)))
    # Or simply np.lexsort(spam[ :, 2:0:-1].astype(int).T)
spam_out = spam[sidx[::-1]]

Sample run -

In [450]: spam
Out[450]: 
array([['Graham', '550', '29'],
       ['John', '90', '1'],
       ['Terry G', '450', '20'],
       ['Eric', '550', '30'],
       ['Terry J', '450', '20'],
       ['Michael', '520', '33']], 
      dtype='|S7')

In [451]: sidx = np.lexsort(( spam[ :, 2 ].astype(int), spam[ :, 1 ].astype(int)))

In [452]: spam[sidx[::-1]]
Out[452]: 
array([['Eric', '550', '30'],
       ['Graham', '550', '29'],
       ['Michael', '520', '33'],
       ['Terry J', '450', '20'],
       ['Terry G', '450', '20'],
       ['John', '90', '1']], 
      dtype='|S7')
Sign up to request clarification or add additional context in comments.

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.