I wanted to sort a multiIndex level which has string and int combo.
mux = pd.MultiIndex.from_arrays([
list('aaaabbbbbccddddd'),
['t1','u','v','w','t12','u','v','w','t11','u','v','w','t4','u','v','w']
], names=['one', 'two'])
df = pd.DataFrame({'col': np.arange(len(mux))}, mux)
df.sort_index(level='two')
Actual
Expectation
target is to order index_level 1 as t1,t4,t11,12,u ……
>Solution :
Use natural sort in parameter key with DataFrame.sort_values:
from natsort import index_natsorted
df = df.sort_values('two', key=lambda x: np.argsort(index_natsorted(x)))
print (df)
col
one two
a t1 0
d t4 12
b t11 8
t12 4
a u 1
b u 5
c u 9
d u 13
a v 2
b v 6
c v 10
d v 14
a w 3
b w 7
d w 11
w 15
Your solution is possible with order of levels, here for second level is used 1:
from natsort import index_natsorted
df = df.sort_index(level=1, key=lambda x: np.argsort(index_natsorted(x)))
print (df)
col
one two
a t1 0
d t4 12
b t11 8
t12 4
a u 1
b u 5
c u 9
d u 13
a v 2
b v 6
c v 10
d v 14
a w 3
b w 7
d w 11
w 15
I also try with level by name, but it seems buggy:
from natsort import index_natsorted
df = df.sort_index(level='two', key=lambda x: np.argsort(index_natsorted(x)))
print (df)
>KeyError: 'Level two not found'

