用 Pandas 计数和排序
Posted
技术标签:
【中文标题】用 Pandas 计数和排序【英文标题】:Count and Sort with Pandas 【发布时间】:2017-03-20 03:19:21 【问题描述】:我有一个用于值的数据框,形成一个文件,我按两列分组,这将返回聚合的计数。现在我想按最大计数值排序,但是我收到以下错误:
KeyError: 'count'
看起来按 agg count 列分组是某种索引,所以不知道该怎么做,我是 Python 和 Panda 的初学者。 这是实际代码,如果您需要更多详细信息,请告诉我:
def answer_five():
df = census_df#.set_index(['STNAME'])
df = df[df['SUMLEV'] == 50]
df = df[['STNAME','CTYNAME']].groupby(['STNAME']).agg(['count']).sort(['count'])
#df.set_index(['count'])
print(df.index)
# get sorted count max item
return df.head(5)
【问题讨论】:
【参考方案1】:我认为您需要添加reset_index
,然后将ascending=False
参数添加到sort_values
因为sort
返回:
FutureWarning:不推荐使用 sort(columns=....),请使用 sort_values(by=.....) .sort_values(['count'], 升序=False)
df = df[['STNAME','CTYNAME']].groupby(['STNAME'])['CTYNAME'] \
.count() \
.reset_index(name='count') \
.sort_values(['count'], ascending=False) \
.head(5)
示例:
df = pd.DataFrame('STNAME':list('abscscbcdbcsscae'),
'CTYNAME':[4,5,6,5,6,2,3,4,5,6,4,5,4,3,6,5])
print (df)
CTYNAME STNAME
0 4 a
1 5 b
2 6 s
3 5 c
4 6 s
5 2 c
6 3 b
7 4 c
8 5 d
9 6 b
10 4 c
11 5 s
12 4 s
13 3 c
14 6 a
15 5 e
df = df[['STNAME','CTYNAME']].groupby(['STNAME'])['CTYNAME'] \
.count() \
.reset_index(name='count') \
.sort_values(['count'], ascending=False) \
.head(5)
print (df)
STNAME count
2 c 5
5 s 4
1 b 3
0 a 2
3 d 1
不过看来你需要Series.nlargest
:
df = df[['STNAME','CTYNAME']].groupby(['STNAME'])['CTYNAME'].count().nlargest(5)
或:
df = df[['STNAME','CTYNAME']].groupby(['STNAME'])['CTYNAME'].size().nlargest(5)
size
和count
的区别是:
size
计数NaN
值,count
不计数。
示例:
df = pd.DataFrame('STNAME':list('abscscbcdbcsscae'),
'CTYNAME':[4,5,6,5,6,2,3,4,5,6,4,5,4,3,6,5])
print (df)
CTYNAME STNAME
0 4 a
1 5 b
2 6 s
3 5 c
4 6 s
5 2 c
6 3 b
7 4 c
8 5 d
9 6 b
10 4 c
11 5 s
12 4 s
13 3 c
14 6 a
15 5 e
df = df[['STNAME','CTYNAME']].groupby(['STNAME'])['CTYNAME']
.size()
.nlargest(5)
.reset_index(name='top5')
print (df)
STNAME top5
0 c 5
1 s 4
2 b 3
3 a 2
4 d 1
【讨论】:
@jul - 可以省略它,因为在您的数据中使用的是 Series,而不是 DataFrame 我正在尝试使用 Series 并获得TypeError: set_index() got an unexpected keyword argument 'name'
确实如此。 df.groupby('track_id').size().reset_index(name='count').sort_values('count', ascending=False)
工作。
我收到错误:TypeError: set_index() got an unexpected keyword argument 'name'
。以下为我工作(差异数据和概率):df[[col1, col2]].groupby(col1).count().sort_values(col2, ascending=False)
@ak2205 - 这意味着它不是Series
,使用.reset_index()
,如果需要,使用rename(columns='index':'col')
【参考方案2】:
我不知道你的 df 到底长什么样。但是,如果您必须按其计数对多个类别的频率进行排序,则从 df 中切出一个系列并对其进行排序会更容易:
series = df.count().sort_values(ascending=False)
series.head()
请注意,本系列将使用类别名称作为索引!
【讨论】:
【参考方案3】:我同意 @Christoph Schranz 从数据帧中提取一系列片段
df[['STNAME','CTYNAME']].groupby('STNAME')['CTYNAME'].count().nlargest(3)
【讨论】:
【参考方案4】:现有的一些答案已经过时。以下解决方案适用于列出列及其不同值的频率:
df = df[col].value_counts(ascending=False).reset_index()
【讨论】:
这对我有用。谢谢!【参考方案5】:要按列数对行进行排序,您可以这样做:
sorted_index = df['col'].value_counts().index
df.set_index('col').loc[sorted_index].reset_index()
如果要保留旧索引,请执行以下操作:
sorted_index = df['col'].value_counts().index
df['index'] = df.index
df.set_index('col', drop=True).loc[sorted_index].reset_index().set_index('index', drop=True)
【讨论】:
以上是关于用 Pandas 计数和排序的主要内容,如果未能解决你的问题,请参考以下文章