pandasagg中的列列表的份额/百分比
我有这种数据框
dat = [{"date": datetime.date(2021,1,1), "c_id" : "a", "var1": 2, "var2": 1, "var3" : 10 },
{"date": datetime.date(2021,1,1), "c_id" : "b", "var1": 2, "var2": 0, "var3" : 20 },
{"date": datetime.date(2021,2,1), "c_id" : "a", "var1": 2, "var2": 1, "var3" : 30 },
{"date": datetime.date(2021,2,1), "c_id" : "b", "var1": 2, "var2": 3, "var3" : 10 },
{"date": datetime.date(2021,3,1), "c_id" : "a", "var1": 2, "var2": 1, "var3" : 30 },
{"date": datetime.date(2021,3,1), "c_id" : "b", "var1": 2, "var2": 3, "var3" : 20 },
]
df = pd.DataFrame(dat)
>>> df
date c_id var1 var2 var3
0 2021-01-01 a 2 1 10
1 2021-01-01 b 2 0 20
2 2021-02-01 a 2 1 30
3 2021-02-01 b 2 3 10
4 2021-03-01 a 2 1 30
5 2021-03-01 b 2 3 20
我希望每个(日期,c_id)拥有这 3 个命名变量的份额。所以例如...
>>> df
date c_id var1 var2 var3 var1_share var2_share var3_share
0 2021-01-01 a 2 1 10 0.15 0.07 0.76
1 2021-01-01 b 2 0 20 0.09 0.00 0.90
2 2021-02-01 a 2 1 30 0.06 0.03 0.90
3 2021-02-01 b 2 3 10 0.13 0.20 0.66
4 2021-03-01 a 2 1 30 0.06 0.03 0.90
5 2021-03-01 b 2 3 20 0.08 0.12 0.80
如果我单独列出这些,我可以以一种愚蠢的方式做到这一点......
>>> df.insert(5, "var1_share", df.apply(lambda x: x["var1"] / x[["var1", "var2", "var3"]].sum(), axis=1))
>>> df
date c_id var1 var2 var3 var1_share
0 2021-01-01 a 2 1 10 0.153846
1 2021-01-01 b 2 0 20 0.090909
2 2021-02-01 a 2 1 30 0.060606
3 2021-02-01 b 2 3 10 0.133333
4 2021-03-01 a 2 1 30 0.060606
5 2021-03-01 b 2 3 20 0.080000
在某些有效列列表上迭代此过程的 Pandas 魔法是什么mylist= ["var1", "var2", "var3"]?我怀疑有一个应用程序可以在单行中做到这一点?
另外,pandas 专家,跨数据帧的列调用此操作会是什么?我确定这很常见,但我不确定如何更好地搜索它。
回答
你可以sum沿着列使用它。
mylist= ["var1", "var2", "var3"]
df[[f'{c}_share' for c in mylist]] = (df[mylist]/df[mylist].sum(axis=1).to_numpy()[:, None]).round(2)
print(df)
date c_id var1 var2 var3 var1_share var2_share var3_share
0 2021-01-01 a 2 1 10 0.15 0.08 0.77
1 2021-01-01 b 2 0 20 0.09 0.00 0.91
2 2021-02-01 a 2 1 30 0.06 0.03 0.91
3 2021-02-01 b 2 3 10 0.13 0.20 0.67
4 2021-03-01 a 2 1 30 0.06 0.03 0.91
5 2021-03-01 b 2 3 20 0.08 0.12 0.80
回答
尝试这个:
cols = pd.Index(['var1', 'var2', 'var3'])
df[cols+'_share'] = df[cols].div(df.sum(axis=1), axis=0)
输出:
date c_id var1 var2 var3 var1_share var2_share var3_share
0 2021-01-01 a 2 1 10 0.153846 0.076923 0.769231
1 2021-01-01 b 2 0 20 0.090909 0.000000 0.909091
2 2021-02-01 a 2 1 30 0.060606 0.030303 0.909091
3 2021-02-01 b 2 3 10 0.133333 0.200000 0.666667
4 2021-03-01 a 2 1 30 0.060606 0.030303 0.909091
5 2021-03-01 b 2 3 20 0.080000 0.120000 0.800000
让我们用大熊猫和内部数据的排列pd.DataFrame.div与参数axis=0和pd.DataFrame.sum使用axis=1。