【问题标题】:Grouping rows from Pandas Dataframe with column value within 20% of first value in group将 Pandas Dataframe 中的行分组,其列值在组中第一个值的 20% 以内
【发布时间】:2021-10-13 18:55:41
【问题描述】:
假设我在下面有一个 Pandas 数据框:
| ID |
value |
| 0 |
1 |
| 1 |
2 |
| 2 |
1.2 |
| 3 |
1.6 |
| 4 |
1.5 |
| 5 |
1.4 |
| 6 |
1.1 |
我想在组的第一个元素的 20% 边距内对值进行分组。
| ID |
value |
group |
| 0 |
1 |
0 |
| 2 |
1.2 |
0 |
| 6 |
1.1 |
0 |
| 1 |
2 |
1 |
| 3 |
1.6 |
1 |
| 4 |
1.5 |
2 |
| 5 |
1.4 |
2 |
最好的方法是什么?
【问题讨论】:
标签:
python
pandas
dataframe
pandas-groupby
rows
【解决方案1】:
试试:
df["group"] = np.nan
group = 0
while (m := df["group"].isna()).any():
val = df.loc[m.idxmax(), "value"]
df.loc[m & (np.abs(df["value"] - val) <= val * 0.2), "group"] = group
group += 1
print(df.sort_values(by="group"))
打印:
ID value group
0 0 1.0 0.0
2 2 1.2 0.0
6 6 1.1 0.0
1 1 2.0 1.0
3 3 1.6 1.0
4 4 1.5 2.0
5 5 1.4 2.0
【解决方案2】:
这是另一种借助函数获取组的解决方案:
def getGroups(df, group):
nullGroupMask = df['group'].isna()
first = df.loc[nullGroupMask, 'value'].iat[0]
df.loc[(df['value'] <= first+first*0.20) & (nullGroupMask), 'group'] = group
return df
df['group'] = float('nan')
group = 0
while True:
df = getGroups(df, group)
group += 1
if not df['group'].isna().any():
break
df = df.astype({'group':int}).sort_values('group')
输出:
ID value group
0 0 1.0 0
2 2 1.2 0
6 6 1.1 0
1 1 2.0 1
3 3 1.6 1
4 4 1.5 1
5 5 1.4 1