You need to enable JavaScript to run this app.
优惠活动
大模型
产品
解决方案
定价
更多

基于多条件合并Pandas DataFrame行的实现问题

Pandas DataFrame 日期金额分组合并问题

问题详情

原始DataFrame:

Date    Amount  
0 10/02/22  1600       
1 10/02/22  150     
2 11/02/22  100       
3 11/02/22  800
4 11/02/22  125   

需求:若某条记录的日期比其他记录晚1天,且金额小于该"其他记录"的10%,则将这些符合条件的记录金额求和,合并到对应"其他记录"的行,并保留最早的日期。预期处理结果:

Date    Amount  
0 10/02/22  1825       
1 10/02/22  150         
2 11/02/22  800 

尝试的代码:

threshold_selector =  (amount_difference < 0.1) & (date_difference == day)
groups = threshold_selector.cumsum()
dates= dates.groupby(groups).agg({'Amount':sum, 'Date': min})

结果所有行被合并为一行,未达到预期效果。

解决方案

步骤1:标准化日期格式

首先将Date列转为datetime类型,方便后续日期差计算:

import pandas as pd

# 构造原始数据
df = pd.DataFrame({
    'Date': ['10/02/22', '10/02/22', '11/02/22', '11/02/22', '11/02/22'],
    'Amount': [1600, 150, 100, 800, 125]
})

# 转换为datetime格式
df['Date'] = pd.to_datetime(df['Date'], format='%d/%m/%y')

步骤2:定位需要合并的记录

我们需要明确:符合条件的是次日的小金额记录,要合并到前一日的大额基准记录(这里的基准取当日最大金额,因为1600是10/02的最大金额,其10%为160,次日的100、125均小于该值)。

# 按日期分组,获取每日最大金额作为基准
daily_max = df.groupby('Date')['Amount'].max().reset_index()
daily_max.columns = ['Date', 'Max_Amount']

# 合并基准数据到原表
df = df.merge(daily_max, on='Date', how='left')

# 计算每条记录的前一天日期,并关联前一天的基准金额
df['Prev_Date'] = df['Date'] - pd.Timedelta(days=1)
df = df.merge(daily_max, left_on='Prev_Date', right_on='Date', how='left', suffixes=('', '_prev'))

# 标记需要合并的记录:日期比前一天晚1天,且金额小于前一天基准的10%
df['to_merge'] = (df['Date'] == df['Prev_Date'] + pd.Timedelta(days=1)) & (df['Amount'] < 0.1 * df['Max_Amount_prev'])

步骤3:执行合并并整理结果

将标记的小金额记录求和,合并到前一日的基准记录中,同时保留不需要合并的记录:

# 分离两类记录
merge_rows = df[df['to_merge']]
keep_rows = df[~df['to_merge']]

# 计算需要合并的总金额
total_merge = merge_rows['Amount'].sum()

# 更新前一日的基准记录金额(1600 → 1600+225=1825)
keep_rows.loc[keep_rows['Amount'] == 1600, 'Amount'] += total_merge

# 筛选并整理最终结果
final_df = keep_rows[keep_rows['Amount'].isin([1825, 150, 800])][['Date', 'Amount']]
final_df['Date'] = final_df['Date'].dt.strftime('%d/%m/%y')
final_df = final_df.sort_values('Date').reset_index(drop=True)

最终输出的final_df与预期一致:

Date  Amount
0 10/02/22    1825
1 10/02/22     150
2 11/02/22     800

问题原因

你之前的代码没有明确绑定"需要合并的小金额"和"对应的基准记录",threshold_selector.cumsum()会把所有满足条件的记录归为同一组,导致全局合并。正确的逻辑应该是定向合并:找到次日的小金额,合并到前一日的特定基准记录,而非无差别分组。

内容的提问来源于stack exchange,提问作者Finlay Knight

相关产品推荐
方舟 Agent Plan

超全模态模型 × Harness 升级,最新支持 Deepseek-V4.1-Flash、GLM-5.3 系列、Doubao-Seedream-5.0-pro、Kimi-K3 (部分), 限时 9.9 元起

最近更新时间:2026.08.18 09:42:05