Pandas groupby:如何获取字符串的并集
- 2025-01-20 09:06:00
- admin 原创
- 109
问题描述:
我有一个像这样的数据框:
A B C
0 1 0.749065 This
1 2 0.301084 is
2 3 0.463468 a
3 4 0.643961 random
4 1 0.866521 string
5 2 0.120737 !
呼唤
In [10]: print df.groupby("A")["B"].sum()
将会回归
A
1 1.615586
2 0.421821
3 0.463468
4 0.643961
现在我想对“C”列执行“相同”操作。由于该列包含字符串,因此 sum() 不起作用(尽管您可能认为它会连接字符串)。我真正想看到的是每个组的字符串列表或集合,即
A
1 {This, string}
2 {is, !}
3 {a}
4 {random}
我一直在尝试寻找方法来做到这一点。
Series.unique() (http://pandas.pydata.org/pandas-docs/stable/generated/pandas.Series.unique.html)不起作用,尽管
df.groupby("A")["B"]
是
pandas.core.groupby.SeriesGroupBy object
所以我希望任何 Series 方法都能奏效。有什么想法吗?
解决方案 1:
In [4]: df = read_csv(StringIO(data),sep='s+')
In [5]: df
Out[5]:
A B C
0 1 0.749065 This
1 2 0.301084 is
2 3 0.463468 a
3 4 0.643961 random
4 1 0.866521 string
5 2 0.120737 !
In [6]: df.dtypes
Out[6]:
A int64
B float64
C object
dtype: object
当您应用自己的函数时,不会自动排除非数字列。不过,这比.sum()
应用于groupby
In [8]: df.groupby('A').apply(lambda x: x.sum())
Out[8]:
A B C
A
1 2 1.615586 Thisstring
2 4 0.421821 is!
3 3 0.463468 a
4 4 0.643961 random
sum
默认连接
In [9]: df.groupby('A')['C'].apply(lambda x: x.sum())
Out[9]:
A
1 Thisstring
2 is!
3 a
4 random
dtype: object
你可以做任何你想做的事
In [11]: df.groupby('A')['C'].apply(lambda x: "{%s}" % ', '.join(x))
Out[11]:
A
1 {This, string}
2 {is, !}
3 {a}
4 {random}
dtype: object
对整个帧执行此操作,一次一组。关键是返回Series
def f(x):
return Series(dict(A = x['A'].sum(),
B = x['B'].sum(),
C = "{%s}" % ', '.join(x['C'])))
In [14]: df.groupby('A').apply(f)
Out[14]:
A B C
A
1 2 1.615586 {This, string}
2 4 0.421821 {is, !}
3 3 0.463468 {a}
4 4 0.643961 {random}
解决方案 2:
您可以使用该apply
方法将任意函数应用于分组数据。因此,如果您想要一个集合,请应用set
。如果您想要一个列表,请应用list
。
>>> d
A B
0 1 This
1 2 is
2 3 a
3 4 random
4 1 string
5 2 !
>>> d.groupby('A')['B'].apply(list)
A
1 [This, string]
2 [is, !]
3 [a]
4 [random]
dtype: object
如果您想要其他东西,只需编写一个执行您想要的操作的函数即可apply
。
解决方案 3:
您可能能够使用aggregate
(或agg
) 函数来连接这些值。(未经测试的代码)
df.groupby('A')['B'].agg(lambda col: ''.join(col))
解决方案 4:
你可以尝试这个:
df.groupby('A').agg({'B':'sum','C':'-'.join})
解决方案 5:
命名聚合pandas >= 0.25.0
从 pandas 0.25.0 版开始,我们已命名聚合,可以对列进行分组、聚合,同时为列分配新名称。这样,我们就不会得到 MultiIndex 列,并且列名根据其包含的数据更有意义:
聚合并获取字符串列表
grp = df.groupby('A').agg(B_sum=('B','sum'),
C=('C', list)).reset_index()
print(grp)
A B_sum C
0 1 1.615586 [This, string]
1 2 0.421821 [is, !]
2 3 0.463468 [a]
3 4 0.643961 [random]
聚合并连接字符串
grp = df.groupby('A').agg(B_sum=('B','sum'),
C=('C', ', '.join)).reset_index()
print(grp)
A B_sum C
0 1 1.615586 This, string
1 2 0.421821 is, !
2 3 0.463468 a
3 4 0.643961 random
解决方案 6:
一个简单的解决方案是:
>>> df.groupby(['A','B']).c.unique().reset_index()
解决方案 7:
如果您想覆盖数据框中的 B 列,可以这样做:
df = df.groupby('A',as_index=False).agg(lambda x:'
'.join(x))
解决方案 8:
按照@Erfan 的好答案,大多数时候在聚合值分析中,您需要这些现有字符值的唯一可能组合:
unique_chars = lambda x: ', '.join(x.unique())
(df
.groupby(['A'])
.agg({'C': unique_chars}))
相关推荐
热门文章
项目管理软件有哪些?
热门标签
曾咪二维码
扫码咨询,免费领取项目管理大礼包!
云禅道AD