根据 pandas 数据框内的列对行求和
Sum rows based on columns inside pandas dataframe
我对 pandas 很陌生,但我使用 python 的水平很好。
我有一个 pandas 数据框,其结构如下
idrun idbasin time q
-192540 1 0 0
-192540 1 1 0.5
...
-192540 2 0 0
-192540 2 1 1
...
-192540 3 0 0
-192540 3 1 1
...
-192541 1 0 0
-192541 1 1 0.5
...
-192541 2 0 0
-192541 2 1 1
...
-192541 3 0 0
-192541 3 1 1
...
这是一个相当大的数据框(7 列和 ~600k 行)。
我想做的是:给定一个元组,其中包含引用 idbasin
列的值(例如 (1,2)
),如果 idrun
值相同
- 对引用的
idbasin
值的 q
列求和,即对于示例,它将是 (1,2)
- 删除与该
idrun
值和元组指定的 idbasin
值对应的行
- 插入求和值
idbasin
等于元组的第一个数字。
参考我的示例df,结果将是
idrun idbasin time q
-192540 1 0 0
-192540 1 1 1.5
...
-192540 3 0 0
-192540 3 1 1
...
-192541 1 0 0
-192541 1 1 1.5
...
-192541 3 0 0
-192541 3 1 1
...
我的解决方案是使用 groupby
将 df
转换为 dict
,然后使用一两个 for 循环执行操作,但我知道迭代 pandas 不是最佳解决方案,所以我相信可能会有一个使用 df
.
的“pandas”解决方案
您可以用 Series.mask
中元组的第一个值替换元组的值,然后聚合 sum
:
tup = (1, 2)
df['idbasin'] = df['idbasin'].mask(df['idbasin'].isin(tup), tup[0])
#alternative
#df['idbasin'] = np.where(df['idbasin'].isin(tup), tup[0], df['idbasin'])
df = df.groupby(['idrun', 'idbasin','time'], as_index=False)['q'].sum()
print (df)
idrun idbasin time q
0 -192541 1 0 0.0
1 -192541 1 1 1.5
2 -192541 3 0 0.0
3 -192541 3 1 1.0
4 -192540 1 0 0.0
5 -192540 1 1 1.5
6 -192540 3 0 0.0
7 -192540 3 1 1.0
我对 pandas 很陌生,但我使用 python 的水平很好。
我有一个 pandas 数据框,其结构如下
idrun idbasin time q
-192540 1 0 0
-192540 1 1 0.5
...
-192540 2 0 0
-192540 2 1 1
...
-192540 3 0 0
-192540 3 1 1
...
-192541 1 0 0
-192541 1 1 0.5
...
-192541 2 0 0
-192541 2 1 1
...
-192541 3 0 0
-192541 3 1 1
...
这是一个相当大的数据框(7 列和 ~600k 行)。
我想做的是:给定一个元组,其中包含引用 idbasin
列的值(例如 (1,2)
),如果 idrun
值相同
- 对引用的
idbasin
值的q
列求和,即对于示例,它将是(1,2)
- 删除与该
idrun
值和元组指定的idbasin
值对应的行 - 插入求和值
idbasin
等于元组的第一个数字。
参考我的示例df,结果将是
idrun idbasin time q
-192540 1 0 0
-192540 1 1 1.5
...
-192540 3 0 0
-192540 3 1 1
...
-192541 1 0 0
-192541 1 1 1.5
...
-192541 3 0 0
-192541 3 1 1
...
我的解决方案是使用 groupby
将 df
转换为 dict
,然后使用一两个 for 循环执行操作,但我知道迭代 pandas 不是最佳解决方案,所以我相信可能会有一个使用 df
.
您可以用 Series.mask
中元组的第一个值替换元组的值,然后聚合 sum
:
tup = (1, 2)
df['idbasin'] = df['idbasin'].mask(df['idbasin'].isin(tup), tup[0])
#alternative
#df['idbasin'] = np.where(df['idbasin'].isin(tup), tup[0], df['idbasin'])
df = df.groupby(['idrun', 'idbasin','time'], as_index=False)['q'].sum()
print (df)
idrun idbasin time q
0 -192541 1 0 0.0
1 -192541 1 1 1.5
2 -192541 3 0 0.0
3 -192541 3 1 1.0
4 -192540 1 0 0.0
5 -192540 1 1 1.5
6 -192540 3 0 0.0
7 -192540 3 1 1.0