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

如何用Pandas检测两个DataFrame行级别列变更并生成明细?

解决思路与完整代码

你已经完成了合并DataFrame的基础步骤,现在我们可以通过矢量化操作(比逐行apply更高效)来批量生成变更检测和描述列,避免重复写多个函数。下面是完整的实现方案:

步骤1:导入依赖并创建示例数据

首先确保你导入了pandas和numpy:

import pandas as pd
import numpy as np

# 示例DataFrame 1
df1 = pd.DataFrame({
    'NAME': ['Jason Kelly', 'Jon Gilman', 'Jessica Lang', 'Bob Wilder', 'Samir Bala'],
    'EMAIL': ['jasonkelly@123.com', 'jongilman@123.com', 'jessicalang@123.com', 'bobwilder@123.com', 'samirbala@123.com'],
    'COUNTRY': ['USA', 'CANADA', 'AUSTRALIA', 'ROMANIA', 'CANADA'],
    'JOBCODE': [1221, 1222, 1221, 1355, 1221],
    'MANAGERNAME': ['Jon Gilman', 'Cindy Lee', 'Esther Donato', 'Mike Lens', 'Ricky Easton']
})

# 示例DataFrame 2
df2 = pd.DataFrame({
    'NAME': ['Jason Kelly', 'Jon Gilman', 'Jessica Lang', 'Bob Wilder', 'Samir Bala'],
    'EMAIL': ['jasonkelly@123.com', 'jongilman@123.com', 'jessicalang@123.com', 'bobwilder@123.com', 'samirbala@123.com'],
    'COUNTRY': ['VIETNAM', 'CANADA', 'AUSTRALIA', 'ROMANIA', 'CANADA'],
    'JOBCODE': [1221, 4464, 2224, 1355, 1221],
    'MANAGERNAME': ['Jon Gilman', 'Sheldon Tracey', 'Esther Donato', 'Emilia Tanner', 'Ricky Easton']
})

步骤2:合并并生成变更列

我们先合并两个DataFrame,然后对COUNTRY、JOBCODE、MANAGERNAME三个列分别生成「是否变更」和「变更内容」列:

# 按EMAIL合并两个DataFrame(只保留共同存在的邮箱)
dfmerge = pd.merge(df1, df2, how='inner', on='EMAIL', suffixes=('_old', '_new'))

# 定义处理单个列变更的逻辑
def generate_change_columns(df, col_name):
    # 生成是否变更列
    change_col = f"{col_name}_CHANGE"
    df[change_col] = np.where(df[f"{col_name}_old"] != df[f"{col_name}_new"], 'YES', 'NO')
    # 生成变更描述列
    movement_col = f"{col_name}_MOVEMENT"
    df[movement_col] = np.where(
        df[change_col] == 'YES',
        df.apply(lambda row: f"FROM {row[f'{col_name}_old']} TO {row[f'{col_name}_new']}", axis=1),
        'NO'
    )

# 批量处理三个目标列
for col in ['COUNTRY', 'JOBCODE', 'MANAGERNAME']:
    generate_change_columns(dfmerge, col)

# 整理最终输出的列(只保留需要的字段)
result_df = dfmerge[[
    'EMAIL', 
    'COUNTRY_CHANGE', 'COUNTRY_MOVEMENT',
    'JOBCODE_CHANGE', 'JOBCODE_MOVEMENT',
    'MANAGERNAME_CHANGE', 'MANAGERNAME_MOVEMENT'
]]

# 重命名MANAGER相关列(和你的期望输出对齐)
result_df = result_df.rename(columns={
    'MANAGERNAME_CHANGE': 'MGR_CHANGE',
    'MANAGERNAME_MOVEMENT': 'MGR_MOVEMENT'
})

print(result_df)

输出结果

运行后你会得到和你期望完全一致的结果:

EMAIL COUNTRY_CHANGE       COUNTRY_MOVEMENT JOBCODE_CHANGE       JOBCODE_MOVEMENT MGR_CHANGE           MGR_MOVEMENT
0  jasonkelly@123.com            YES        FROM USA TO VIETNAM             NO                      NO         NO                      NO
1   jongilman@123.com             NO                      NO            YES  FROM 1222 TO 4464        YES  FROM Cindy Lee TO Sheldon Tracey
2  jessicalang@123.com            NO                      NO            YES  FROM 1221 TO 2224        NO                      NO
3   bobwilder@123.com            NO                      NO             NO                      NO        YES  FROM Mike Lens TO Emilia Tanner
4    samirbala@123.com            NO                      NO             NO                      NO         NO                      NO

关键说明

  • 用numpy.where做矢量化判断,比apply(axis=1)效率高很多,适合大数据量场景;
  • 封装了通用函数generate_change_columns,避免重复代码,后续要加其他列的话直接在循环里加即可;
  • 通过suffixes参数给合并后的列加_old和_new后缀,更清晰区分新旧数据;
  • 最后重命名了经理相关的列,和你的期望输出格式对齐。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.05.08 17:57:54