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

如何比较标签不同的DataFrame并获得df.compare格式的结果?

如何对比索引和列标签均不同的DataFrame并输出类似df.compare的格式

原生pd.DataFrame.compare()要求两个DataFrame必须索引和列完全匹配,直接用它对比列或索引不同的DataFrame必然报错。要实现类似格式的对比,需先对齐两个DataFrame的索引和列,再筛选差异并整理格式。

分场景处理

场景1:存在部分相同列(如L和R)

L和R共享FellowshipID和FirstName列,可基于这两列对齐数据后对比差异:

import pandas as pd

L = pd.DataFrame(
{
  'FellowshipID': [1001, 1002, 1003, 1004],
  'FirstName': ['Frodo', 'Samwise', 'Gandalf', 'Pippin'], 
  'Skills': ['Hiding', 'Gardening', 'Spells', 'Fireworks']
}    
)

R = pd.DataFrame(
    {
        'FellowshipID': [1001, 1002, 1006, 1007, 1008], 
        'FirstName': ['Frodo', 'Samwise', 'Legolas', 'Elrond', 'Barromir'], 
        'Age': [50, 39, 2931, 6520, 51]    
    }
)

# 1. 按共同列外连接对齐所有行
merged = pd.merge(L, R, on=['FellowshipID', 'FirstName'], how='outer', suffixes=('_L', '_R'))

# 2. 整理成compare风格的多层列结构
all_columns = sorted(set(col.rsplit('_', 1)[0] for col in merged.columns))
result = pd.DataFrame()

for col in all_columns:
    col_L = f"{col}_L"
    col_R = f"{col}_R"
    # 标记差异行(含一方为空的情况)
    diff_mask = (merged[col_L] != merged[col_R]) | merged[col_L].isna() | merged[col_R].isna()
    # 提取差异数据并重命名列
    diff_data = merged.loc[diff_mask, [col_L, col_R]]
    diff_data.columns = pd.MultiIndex.from_tuples([('self', col), ('other', col)])
    result = pd.concat([result, diff_data], axis=1)

# 调整列顺序,和原生compare输出一致
result = result.reindex(columns=[('self', col) for col in all_columns] + [('other', col) for col in all_columns])
print(result)

输出会保留self(对应L)和other(对应R)的多层列结构,仅展示有差异的行。

场景2:无任何相同列(如L和N)

无共同列时,按行位置对齐数据后对比:

N = pd.DataFrame(
    data = {
        'Relation': ['fri 1', 'fri 2', 'fri 3', 'fri 4'],
        'Name': ['John', 'Jane', 'Adam', 'Omar'],
        'Char': ['Hw', 'Amb', 'Adv', 'Sprt']
    }
)

# 统一索引长度,按行位置对齐
max_len = max(len(L), len(N))
L_aligned = L.reindex(range(max_len))
N_aligned = N.reindex(range(max_len))

# 合并并筛选差异行
merged = pd.concat([L_aligned, N_aligned], axis=1, keys=['self', 'other'])
diff_mask = merged.apply(lambda x: not x['self'].equals(x['other']), axis=1)
result = merged[diff_mask]
print(result)

这段代码会按行位置对齐两个DataFrame,仅展示存在差异的行,列结构与compare格式一致。

核心逻辑

原生compare的本质是对齐索引和列→筛选差异行→整理多层列格式,自定义实现只需遵循这三个步骤,对齐方式可根据业务场景选择:有唯一标识列时优先用标识列对齐,无标识列则按行位置对齐。

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

相关产品推荐
方舟 Agent Plan

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

最近更新时间:2026.06.19 13:47:19