对包含文本和字符串的multiindex数据框的索引进行排序

问题描述

我有一个Multi Index数据框,所以我想根据同时包含文本和数字的ID2对其进行排序。 我正在使用Python 3.7

MultiIndex([(1,'HK_MN001'),(2,(3,'HK_MN002'),(4,'HK_MN003'),(5,'HK_MN004'),(6,'HK_MN005'),(7,(8,'HK_MN005')],names=['ID1','ID2'])

我尝试了这段代码,但给了我错误

a = final_df1.index.get_level_values(1).to_series().str.extract('(\d+)',expand=False).astype(int).sort_values()

final_df1 = final_df1.reindex(index=a.index)

错误

final_df1 = final_df1.reindex(index=a.index)  # error at this line
TypeError: Expected tuple,got str

解决方法

如果需要在第二级中按数字排序,则可以使用,将转换级别转换为Series,删除sort_values并添加Index.argsort作为排序值的位置,因此更改顺序可以传递给{ {3}}:

mux = pd.MultiIndex.from_tuples([(1,'HK_MN001'),(2,(3,'HK_MN002'),(4,'HK_MN003'),(5,'HK_MN004'),(6,'HK_MN005'),(7,(8,'HK_MN005')],names=['ID1','ID2'])

final_df1 = pd.DataFrame({'a':range(8)},index=mux)
print (final_df1)
              a
ID1 ID2        
1   HK_MN001  0
2   HK_MN001  1
3   HK_MN002  2
4   HK_MN003  3
5   HK_MN004  4
6   HK_MN005  5
7   HK_MN005  6
8   HK_MN005  7

a = final_df1.index.get_level_values(1).str.extract('(\d+)',expand=False).astype(int)
print (a)
Int64Index([1,1,2,3,4,5,5],dtype='int64',name='ID2')

df = final_df1.iloc[a.argsort()]
print (df)
              a
ID1 ID2        
1   HK_MN001  0
2   HK_MN001  1
3   HK_MN002  2
4   HK_MN003  3
5   HK_MN004  4
6   HK_MN005  5
7   HK_MN005  6
8   HK_MN005  7

但是,如果可能的话,更简单的方法是使用DataFrame.iloc,如果可能的话,按文本和数字一起排序:

df = final_df1.sort_index(level=1)