【发布时间】:2019-08-29 21:25:42
【问题描述】:
给定 df1 和 df2,我想得到 df3。我想匹配的唯一列/行是 Pop 和 Homes。我已经包含了 Other 数据列,以获得任意数量的列的解决方案。
df1
City Pop Homes Other
City_1 100 1 0
City_1 100 2 6
City_1 100 2 2
City_1 100 3 9
City_1 200 1 6
City_1 200 2 6
City_1 200 3 7
City_1 300 1 0
df2
City Pop Homes Other
City_1 100 1 0
City_1 100 2 6
City_1 100 2 2
City_1 100 8 9
City_1 200 1 6
City_1 200 2 6
City_1 800 3 7
City_1 800 8 0
df3
City Pop Homes Other
City_1 100 1 0
City_1 100 2 6
City_1 100 2 2
City_1 200 1 6
City_1 200 2 6
我考虑过按 City、Pop 和 Homes 分组,例如 df1.groupby(['City', 'Pop', 'Homes']),但后来我不知道如何过滤掉 Pop 和 Homes。
编辑
这是我的代码,因此您可以更轻松地帮助我。
df1_string = """City_1 100 1 0
City_1 100 2 6
City_1 100 2 2
City_1 100 3 9
City_1 200 1 6
City_1 200 2 6
City_1 200 3 7
City_1 300 1 0"""
df2_string = """City_1 100 1 0
City_1 100 2 6
City_1 100 2 2
City_1 100 8 9
City_1 200 1 6
City_1 200 2 6
City_1 800 3 7
City_1 800 8 0"""
df1 = pd.DataFrame([x.split() for x in df1_string.split('\n')], columns=['City', 'Pop', 'Homes', 'Other'])
df2 = pd.DataFrame([x.split() for x in df2_string.split('\n')], columns=['City', 'Pop', 'Homes', 'Other'])
df1_keys = [x for x in df1.groupby(['Pop', 'Homes']).groups.keys()]
df2_keys = [x for x in df2.groupby(['Pop', 'Homes']).groups.keys()]
print(df1_keys)
[('100', '1'), ('100', '2'), ('100', '3'), ('200', '1'), ('200', '2'), ('200', '3'), ('300', '1')]
print(df2_keys)
[('100', '1'), ('100', '2'), ('100', '8'), ('200', '1'), ('200', '2'), ('800', '3'), ('800', '8')]
从这里过滤掉不相等的组对似乎很简单,但我无法解决这个问题。我试过了:
df1 = df1[df1.groupby(['Pop', 'Homes']).groups.keys().isin(df2.groupby(['Pop', 'Homes']).groups.keys())]
以及当它不起作用时的其他变体 - 但我感觉它接近工作了。
解决方案
df1.set_index(['Pop', 'Homes'], inplace=True)
df2.set_index(['Pop', 'Homes'], inplace=True)
df1 = df1[df2.index.isin(df1.index)]
df1.reset_index(inplace=True)
【问题讨论】:
-
添加minimal reproducible example 将极大地帮助那些提供有效答案的人。但你在下面得到了很好的答案。
-
@RichAndrews 我进行了编辑。现在应该更清楚了
-
看起来不错。你知道人们将数据“复制”到他们的计算机剪贴板和
pandas.read_clipboard()吗?超级方便。我认为你的 Q 中也有你的代码尝试,没有理由排除它。但是你有很好的答案要复习!
标签: python-3.x pandas filter group-by