我试图突出显示两个数据帧之间的确切变化 .
假设我有两个Python Pandas数据帧:
"StudentRoster Jan-1":
id Name score isEnrolled Comment
111 Jack 2.17 True He was late to class
112 Nick 1.11 False Graduated
113 Zoe 4.12 True
"StudentRoster Jan-2":
id Name score isEnrolled Comment
111 Jack 2.17 True He was late to class
112 Nick 1.21 False Graduated
113 Zoe 4.12 False On vacation
我的目标是输出一个HTML表:
-
标识已更改的行(可以是int,float,boolean,string)
-
输出具有相同,OLD和NEW值的行(理想情况下输入到HTML表中),以便消费者可以清楚地看到两个数据帧之间发生了什么变化:
"StudentRoster Difference Jan-1 - Jan-2":
id Name score isEnrolled Comment
112 Nick was 1.11| now 1.21 False Graduated
113 Zoe 4.12 was True | now False was "" | now "On vacation"
我想我可以逐行和逐列比较,但有更简单的方法吗?
11 回答
第一部分类似于Constantine,你可以得到哪些行为空的布尔值*:
然后我们可以看到哪些条目已更改:
这里第一个条目是索引,第二个条目是已更改的列 .
*注意:
df1
和df2
在此处共享相同的索引非常重要 . 为了克服这种歧义,您可以确保只使用df1.index & df2.index
查看共享标签,但我想我会将其作为练习 .突出显示两个DataFrame之间的差异
可以使用DataFrame样式属性突出显示存在差异的单元格的背景颜色 .
Using the example data from the original question
第一步是使用
concat
函数水平连接DataFrames,并使用keys
参数区分每个帧:交换列级别并将相同的列名称放在一起可能更容易:
现在,更容易发现帧中的差异 . 但是,我们可以进一步使用
style
属性来突出显示不同的单元格 . 我们定义了一个自定义函数来执行此操作,您可以在this part of the documentation中看到 .这将突出显示两个都缺少值的单元格 . 您可以填写它们或提供额外的逻辑,以便它们不会突出显示 .
这个答案简单地扩展了@Andy Hayden,使其在数字字段为
nan
时具有弹性,并将其包装到函数中 .因此,使用您的数据(稍微编辑以在分数列中包含NaN):
输出:
我遇到过这个问题,但在找到这篇文章之前找到了答案:
根据unutbu的答案,加载您的数据......
...定义你的差异功能......
然后你可以简单地使用Panel得出结论:
顺便说一句,如果您在IPython Notebook中,您可能希望使用彩色diff函数来根据单元格是否不同,相等或左/右null来给出颜色:
版画
如果您的两个数据帧中包含相同的ID,那么找出更改的内容实际上非常简单 . 只需执行
frame1 != frame2
将为您提供一个布尔数据框架,其中每个True
都是已更改的数据 . 从那里,你可以通过changedids = frame1.index[np.any(frame1 != frame2,axis=1)]
轻松获得每个更改行的索引 .使用concat和drop_duplicates的另一种方法:
输出:
扩展@cge的答案,这对于结果的可读性来说非常酷:
完整演示示例:
在摆弄@journois的答案之后,由于Panel's deprication,我能够使用MultiIndex而不是Panel来使用它 .
首先,创建一些虚拟数据:
然后,定义你的diff函数,在这种情况下我将使用他的答案中的那个
report_diff
保持不变:然后,我将把数据连接成一个MultiIndex数据帧:
最后,我将在每个列组中应用
report_diff
:这输出:
这就是全部!
以下是使用select和merge的另一种方法:
以下是Jupyter截图中的相同内容:
找到两个数据帧之间不对称差异的函数如下所示:(基于set difference for pandas)GIST:https://gist.github.com/oneryalcin/68cf25f536a25e65f0b3c84f9c118e03
例: