pandas-排序

发布时间 2023-09-16 10:35:10作者: 贝壳里的星海

pandas-排序

Pandas 提供了多种排序数据的方法

sort_values()值排序

作用:既可以根据列数据,也可根据行数据排序

DataFrame.sort_values(by, axis=0, ascending=True, inplace=False, kind='quicksort', na_position='last')

axis:     {0 or ‘index’, 1 or ‘columns’}, default 0,默认按照列排序,即纵向排序;如果为1,则是横向排序。
by:       str or list of str;如果axis=0,那么by="列名";如果axis=1,那么by="行名"。
ascending:布尔型,True则升序,如果by=['列名1','列名2'],则该参数可以是[True, False]
inplace:  布尔型,是否用排序后的数据框替换现有的数据框。
kind:	  排序方法,{‘quicksort’, ‘mergesort’, ‘heapsort’}
na_position:{‘first’, ‘last’}, default ‘last’,默认缺失值排在最后面。
import pandas as pd  
  
# 创建一个 Series  
s = pd.Series([3, 1, 4, 1, 5, 9, 2, 6, 5, 3, 5])  
  
# 按值排序  
sorted_s = s.sort_values()  
print(sorted_s)

# 1     1
# 3     1
# 6     2
# 0     3
# 9     3
# 2     4
# 4     5
# 8     5
# 10    5
# 7     6
# 5     9
# dtype: int64

对 DataFrame 按一列排序

import pandas as pd  
  
# 创建一个 DataFrame  
df = pd.DataFrame({  
    'A': [3, 1, 4, 1, 5, 9, 2, 6, 5, 3, 5],  
    'B': [7, 4, 9, 1, 8, 6, 3, 5, 2, 8, 7]  
})  
  
# 按 A 列的值排序  
sorted_df = df.sort_values(by='B')  
print(sorted_df)

#     A  B
# 3   1  1
# 8   5  2
# 6   2  3
# 1   1  4
# 7   6  5
# 5   9  6
# 0   3  7
# 10  5  7
# 4   5  8
# 9   3  8
# 2   4  9

对 DataFrame 按多列排序

import pandas as pd  
  
# 创建一个 DataFrame  
df = pd.DataFrame({  
    'A': [3, 1, 4, 1, 5, 9, 2, 6, 5, 3, 5],  
    'B': [7, 4, 9, 1, 8, 6, 3, 5, 2, 8, 7],  
    'C': [0, 1, 9, 2, 5, 1, 8, 6, 3, 5, 2]  
})  
  
# 按 A 和 C 列的值排序  
sorted_df = df.sort_values(by=['A', 'C'])  
print(sorted_df)

#     A  B  C
# 1   1  4  1
# 3   1  1  2
# 6   2  3  8
# 0   3  7  0
# 9   3  8  5
# 2   4  9  9
# 10  5  7  2
# 8   5  2  3
# 4   5  8  5
# 7   6  5  6
# 5   9  6  1
import pandas as pd  
df = pd.DataFrame({'b':[1,2,3,2],
                   'a':[4,3,2,1],
				   'c':[1,3,8,2]},index=[2,0,1,3]) 

sorted_df=df.sort_values(by=[3,0],axis=1,ascending=[True,False])
print(sorted_df)
#    a   c   b
#2   4   1   1
#0   3   3   2
#1   2   8   3
#3   1   2   2

sort_index()标签排序

默认根据行标签对所有行排序,或根据列标签对所有列排序,或根据指定某列或某几列对行排序。

sort_index(axis=0, level=None, ascending=True, inplace=False, kind='quicksort', na_position='last', sort_remaining=True, by=None)

axis:	  0按照行名排序;1按照列名排序
level:	  默认None,否则按照给定的level顺序排列---貌似并不是,文档
ascending:默认True升序排列;False降序排列
inplace:  默认False,否则排序之后的数据直接替换原来的数据框
kind:	  排序方法,{‘quicksort’, ‘mergesort’, ‘heapsort’}, default ‘quicksort’。似乎不用太关心。
na_position:缺失值默认排在最后{"first","last"}
by:		  按照某一列或几列数据进行排序
import pandas as pd  
df = pd.DataFrame({'b':[1,2,2,3],'a':[4,3,2,1],'c':[1,3,8,2]},index=[2,0,1,3]) 
print(df)
#    b   a   c
#2   1   4   1
#0   2   3   3
#1   3   2   8
#3   2   1   2

sorted_df=df.sort_index(axis=1)  # 按'列标签'升序排序
print(sorted_df)
#	a   b   c
#2   4   1   1
#0   3   2   3
#1   2   3   8
#3   1   2   2

nlargest()

函数用于从 DataFrame 或 Series 中获取最大的几个元素

DataFrame.nlargest(self, n, columns, keep='first')
n 		 是你想获取的最大元素个数。
columns  标签或标签列表
keep      {'first','last','all'}

并非所有列类型都可以使用此功能。例如,当指定带有object或category dtypes的列时,TypeError引发。
import pandas as pd  
  
data = {  
    'A': [4, 7, 1, 8, 3],  
    'B': [9, 6, 2, 1, 5],  
    'C': [0, 3, 8, 6, 7]  
}  
  
df = pd.DataFrame(data)  
result = df.nlargest(3, 'A', keep='last')  
print(result)

#   A  B  C
#3  8  1  6
#1  7  6  3
#0  4  9  0

rank()排名

排名和排序的区别在于排序一定是有顺序,而排名分先后并列。如在现实生活中相同的分数存在排名并列的情况。

DataFrame.rank(axis=0,method='average',numeric_only=None,na_option='keep',ascending=True,pct=False)

参数说明:
axis:	0或'index',1或'columns',默认0,沿着行或列计算排名
method: 'average','min','max','first','dense',默认为'average',如何对具有相同值(即ties)的记录组进行排名:
average:组的平均等级
min:	组中最低的排名
max:	组中最高等级
first:   按排列顺序排列,依次排列
dense: 	类似于 ‘min’,但组之间的排名始终提高1
numeric_only:bool,是否仅仅计算数字型的columns,布尔值
na_option:{'keep','top','bottom'},默认为'keep',NaN值是否参与排名及如何排名
keep:	将NaN等级分配给NaN值
top:	如果升序,则将最小等级分配给NaN值
bottom:	如果升序,则将最高等级分配给NaN值。
ascending:bool,默认为True,元素是否应该按升序排名。
pct:	  bool,默认为False,是否以百分比形式显示返回的排名

import pandas as pd
# 创建一个DataFrame对象
data = pd.DataFrame({'班级':['1班','1班','1班','1班','1班','2班','2班','2班','2班','2班'],
                     '姓名':['韩愈','柳宗元','欧阳修','苏洵','苏轼','苏辙','曾巩','王安石','张三','小伍哥'],
                     '成绩':[80,70,70,40,10,60,60,50,50,40]})

# 数据对齐
data['姓名'] = data['姓名'].str.ljust(3,'一') 
print(data)
#    班级   姓名  成绩
# 0  1班  韩愈一  80
# 1  1班  柳宗元  70
# 2  1班  欧阳修  70
# 3  1班  苏洵一  40
# 4  1班  苏轼一  10
# 5  2班  苏辙一  60
# 6  2班  曾巩一  60
# 7  2班  王安石  50
# 8  2班  张三一  50
# 9  2班  小伍哥  40

#为了简化,我们只选择1班的成绩来看

data_1 = data[data['班级']=='1班']
data_1['rank']       = data_1['成绩'].rank(ascending=False) 
data_1['rank_min']   = data_1['成绩'].rank(method='min',ascending=False) 
data_1['rank_max']   = data_1['成绩'].rank(method='max',ascending=False) 
data_1['rank_first'] = data_1['成绩'].rank(method='first',ascending=False) 
data_1['rank_dense'] = data_1['成绩'].rank(method='dense',ascending=False)

print(data_1)
#    班级   姓名  成绩  rank  rank_min  rank_max  rank_first  rank_dense
# 0  1班  韩愈一  80   1.0       1.0       1.0         1.0         1.0
# 1  1班  柳宗元  70   2.5       2.0       3.0         2.0         2.0
# 2  1班  欧阳修  70   2.5       2.0       3.0         3.0         2.0
# 3  1班  苏洵一  40   4.0       4.0       4.0         4.0         3.0
# 4  1班  苏轼一  10   5.0       5.0       5.0         5.0         4.0

method='first'时,当里两个人的分数相同时,分数相同的情况下,谁先出现谁的排名靠前
method='min'时,  分数相同时,取在顺序排名中最小的那个排名作为该值的排名,会出现跳空
method='max'时,  分数相同时,取在顺序排名中最大的那个排名作为该值的排名,会出现跳空
method='dense', dense是稠密的意思,即相同成绩的同学排名相同,其他依次加1即可,不会出现名次跳空的情况
参数pct=True时,返回排名的分位数,可以用于计算排名的百分比,非常方便。
data_1 = data[data['班级']=='1班']
data_1['成绩_first'] = data_1['成绩'].rank(method='first',ascending=False,pct=True)
print(data_1)
#班级   姓名  成绩  成绩_first
#0  1班  〇韩愈  80       0.2
#1  1班  柳宗元  70       0.4
#2  1班  欧阳修  70       0.6
#3  1班  〇苏洵  40       0.8
#4  1班  〇苏轼  10       1.0

参考资料

https://blog.csdn.net/fengdu78/article/details/120170431

https://www.cnblogs.com/wang_yb/p/17419790.html