如何比较两个Pandas数据框并在一个文件中删除重复项,而不附加来自其他文件的数据。

5
我将尝试使用Pandas数据框比较两个CSV文件。其中一个是主表(test_master.csv),每天都会向其追加数据;另一个是每日报告(test_daily.csv),包含我想要添加到test_master.csv的数据。
我从这些文件中创建了两个Pandas数据框:
import pandas as pd

dfmaster = pd.read_csv(test_master.csv)
dfdaily = pd.read_csv(test_daily.csv)

我希望将每日清单与主清单进行比较,以查看每日清单中是否存在已在主清单中的重复行。如果有,则要从dfdaily中删除重复项。然后,我想将这些非重复数据写入dfmaster。
重复数据始终是整个行。我的计划是逐行遍历工作表进行比较。
我意识到我可以将每日数据附加到dfmaster数据框中,并使用drop_duplicates来删除重复项。但我无法弄清楚如何删除dfdaily数据框中的重复项。而且我需要能够将dfdaily数据写回test_daily.csv(或另一个新文件),不包括重复数据。
以下是数据框可能的示例。
test_master.csv
  column 1   |  column 2   |  column 3   |
+-------------+-------------+-------------+
| 1           | 2           | 3           |
| 4           | 5           | 6           |
| 7           | 8           | 9           |
| duplicate 1 | duplicate 1 | duplicate 1 |
| duplicate 2 | duplicate 2 | duplicate 2

test_daily.csv

+-------------+-------------+-------------+
|  column 1   |  column 2   |  column 3   |
+-------------+-------------+-------------+
| duplicate 1 | duplicate 1 | duplicate 1 |
| duplicate 2 | duplicate 2 | duplicate 2 |
| 10          | 11          | 12          |
| 13          | 14          | 15          |
+-------------+-------------+-------------+

期望的输出是:
test_master.csv
+-------------+-------------+-------------+
|  column 1   |  column 2   |  column 3   |
+-------------+-------------+-------------+
| 1           | 2           | 3           |
| 4           | 5           | 6           |
| 7           | 8           | 9           |
| duplicate 1 | duplicate 1 | duplicate 1 |
| duplicate 2 | duplicate 2 | duplicate 2 |
| 10          | 11          | 12          |
| 13          | 14          | 15          |
+-------------+-------------+-------------+

test_daily.csv

+----------+----------+----------+
| column 1 | column 2 | column 3 |
+----------+----------+----------+
|       10 |       11 |       12 |
|       13 |       14 |       15 |
+----------+----------+----------+

非常感谢您的帮助!

编辑

我最初错误地认为来自集合差异问题的解决方案可以解决我的问题。 我遇到了某些情况,其中那些解决方案无法正常工作。 我相信这与索引编号标签有关,如Troy D在下面的评论中提到的。 Troy D的解决方案是我现在正在使用的解决方案。


接受的答案仅在数据框具有相同的行索引标签时才有效,这似乎不是这个问题的情况,因此我认为这不是https://dev59.com/ZWMl5IYBdhLWcg3wuI7p的重复。 - Troy D
1个回答

4

尝试以下方法:

我创建了2个索引,然后将行2-4设置为重复行:

import numpy as np

test_master = pd.DataFrame(np.random.rand(3, 3), columns=['A', 'B', 'C'])
test_daily = pd.DataFrame(np.random.rand(5, 3), columns=['A', 'B', 'C'])
test_daily.iloc[1:4] = test_master[:3].values

print(test_master)
print(test_daily)

输出:

      A         B         C
0  0.009322  0.330057  0.082956
1  0.197500  0.010593  0.356774
2  0.147410  0.697779  0.421207
      A         B         C
0  0.643062  0.335643  0.215443
1  0.009322  0.330057  0.082956
2  0.197500  0.010593  0.356774
3  0.147410  0.697779  0.421207
4  0.973867  0.873358  0.502973

然后,添加多级索引以标识哪些数据来自哪个数据框:
test_master['master'] = 'master'
test_master.set_index('master', append=True, inplace=True)
test_daily['daily'] = 'daily'
test_daily.set_index('daily', append=True, inplace=True)

现在按照您的建议合并并删除重复项:

merged = test_master.append(test_daily)
merged = merged.drop_duplicates().sort_index()
print(merged)

输出:

             A         B         C
  master                              
0 daily   0.643062  0.335643  0.215443
  master  0.009322  0.330057  0.082956
1 master  0.197500  0.010593  0.356774
2 master  0.147410  0.697779  0.421207
4 daily   0.973867  0.873358  0.502973

现在你可以看到带有数据来源标签的组合数据框。现在只需要对每日数据进行切片:

idx = pd.IndexSlice
print(merged.loc[idx[:, 'daily'], :])

输出:

             A         B         C
  master                              
0 daily   0.643062  0.335643  0.215443
4 daily   0.973867  0.873358  0.502973

谢谢Troy D. 我开始遇到一些情况,上面链接的Set Difference问题的答案失败了。你的解决方案似乎产生了我正在寻找的确切结果。 - Philalethes
Troy D. - 你知道为什么上述代码只有我手动打开和重新保存我从中构建“每日数据框架”的“daily”csv文件才起作用吗? 我运行一份报告,并每晚自动将其保存到一个csv文件中。 如果我只是在这个“daily” csv文件上运行我的程序,上面的代码就不会删除重复项。 当我查看数据框架时,它们似乎是相同的。 但是,如果我简单地手动打开、保存并关闭“ daily ”csv文件,那么程序就会删除重复项。 我无法解决这个问题。 我已经尝试了很多变通方法,但没有成功。 - Philalethes
你是在Excel中打开它吗?如果你打开并保存CSV文件,Excel会在值周围添加单引号。虽然在Excel中看起来一样,但实际上已经被更改了。如果你使用文本编辑器查看文件,就能看到区别。然后,CSV读取器将根据数据格式的不同而有所不同。这应该是我的第一个猜测。 - Troy D
这就是它。在文本编辑器中,我看到原始的csv文件每个值都有“ ”。在我将其保存在Excel中并在文本编辑器中重新打开它后,“ ”不再存在。有什么简单的解决方法吗? - Philalethes
如果您正在使用pd.read_csv(),则"sep="选项允许您指定文件中分隔符的样式。我不确定什么样的分隔符适用于您的文件,但也许可以查看https://superuser.com/questions/1184776/read-csv-using-pandas-with-values-enclosed-with-double-quotes-and-values-have-co/1257803。 - Troy D

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接