我有一个数据框
ID 2014-01-01 2015-01-01 2016-01-01
1 NaN 0.1 0.2
2 0.1 0.3 0.5
3 0.2 NaN 0.7
4 0.8 0.4 0.1
对于每个日期(col),我想获得每个id的等级。例如,在col' 2014-01-01'中,id = 4具有最大值,因此我们将等级1分配给id = 4.id = 3具有第二大值,因此我们将其赋予等级2。如果数据是NaN,则忽略它。
ID 2014-01-01 2015-01-01 2016-01-01
1 NaN 3 3
2 3 2 2
3 2 NaN 1
4 1 1 4
下一步是获取每个ID的平均排名。例如,id1 =(4 + 3)/ 2 = 3.5的AvgRank和id2的AvgRank =(3 + 2 + 2)/ 3 = 2.33
ID AvgRank
1 3
2 2.33
3 1.5
4 2
我的算法是:
为每个id创建一个字典({str:list}) - >循环遍历所有列 - >对于每列计算排名并更新到字典中的列表
但我觉得这个简单的问题太复杂了。 有没有简单的方法来获得avgrank表?
以下是创建数据框的代码
df = pd.DataFrame({'ID':[1,2,3,4],'2014-01-01':[float('NaN'),0.1,0.2,0.8],
'2015-01-01':[0.1,0.3,float('NaN'),0.4],'2016-01-01':[0.2,0.5,0.7,0.1]})
答案 0 :(得分:2)
目前还不清楚为什么你认为rank
对于第二列中的第一行值应为4
,但以下内容为您提供了所需内容。在这里,我们在感兴趣的列上调用rank
并传递method='dense'
和ascending=False
,使其排名正确:
In [60]:
df.ix[:, :-1].rank(method='dense', ascending=False)
Out[60]:
2014-01-01 2015-01-01 2016-01-01
0 NaN 3 3
1 3 2 2
2 2 NaN 1
3 1 1 4
我们然后concat
来自orig df的单个列和rename
mean
的结果以及axis=1
的行方式意味着:
In [67]:
pd.concat([df['ID'], df.ix[:, :-1].rank(method='dense', ascending=False).mean(axis=1)], axis=1).rename(columns={0:'AvgRank'})
Out[67]:
ID AvgRank
0 1 3.000000
1 2 2.333333
2 3 1.500000
3 4 2.000000