当两个数据框都包含重复键时,如何将两个熊猫数据框与左连接合并?

Posted

技术标签:

【中文标题】当两个数据框都包含重复键时,如何将两个熊猫数据框与左连接合并?【英文标题】:How to merge two pandas dataframe with left join when both dataframe contains duplicate keys? 【发布时间】:2018-04-08 20:07:54 【问题描述】:

我有两个 Python Pandas 数据框,如下所示:

left = pd.DataFrame('key1': ['K0', 'K0', 'K1', 'K1', 'K1', 'K1', 'K2'],
                      'key2': ['K0', 'K1', 'K0', 'K0', 'K0', 'K0', 'K1'],
                      'A': ['A0', 'A1', 'A2', 'A3', 'A4', 'A5', 'A6'],
                      'B': ['B0', 'B1', 'B2', 'B3', 'B4', 'B5', 'B6'])

right = pd.DataFrame('key1': ['K0', 'K1', 'K1', 'K2'],
                       'key2': ['K0', 'K0', 'K0', 'K0'],
                       'C': ['C0', 'C1', 'C2', 'C3'],
                       'D': ['D0', 'D1', 'D2', 'D3'])
print left
    A   B key1 key2
0  A0  B0   K0   K0
1  A1  B1   K0   K1
2  A2  B2   K1   K0
3  A3  B3   K1   K0
4  A4  B4   K1   K0
5  A5  B5   K1   K0
6  A6  B6   K2   K1

print right
    C   D key1 key2
0  C0  D0   K0   K0
1  C1  D1   K1   K0
2  C2  D2   K1   K0
3  C3  D3   K2   K0

我想在特定条件下合并这两个数据框:

    我想在 key1 和 key2 上合并这个数据帧。 我想要输出数据框,其中只有左侧数据框中的行可用。 (如果左侧 Dataframe 的 key1 和 key2 在右侧 Dataframe 的 key1 和 key2 中可用,则通过附加列 C 和 D 来满足当前行)

我尝试如下:

result = pd.merge(left, right, on=['key1', 'key2'],how = 'left')
print result

# Output - which is not expected for me
     A   B key1 key2    C    D
0   A0  B0   K0   K0   C0   D0
1   A1  B1   K0   K1  NaN  NaN
2   A2  B2   K1   K0   C1   D1
3   A2  B2   K1   K0   C2   D2
4   A3  B3   K1   K0   C1   D1
5   A3  B3   K1   K0   C2   D2
6   A4  B4   K1   K0   C1   D1
7   A4  B4   K1   K0   C2   D2
8   A5  B5   K1   K0   C1   D1
9   A5  B5   K1   K0   C2   D2
10  A6  B6   K2   K1  NaN  NaN

如果我从左侧 Dataframe 中删除重复的条目,那么我也没有得到预期的输出。

然后,我尝试从结果 Dataframe 中删除重复条目,然后我得到以下 Dataframe:

result.drop_duplicates(subset = ['A','B','key1','key2'], inplace=True)
print result

     A   B key1 key2    C    D
0   A0  B0   K0   K0   C0   D0
1   A1  B1   K0   K1  NaN  NaN
2   A2  B2   K1   K0   C1   D1
4   A3  B3   K1   K0   C1   D1
6   A4  B4   K1   K0   C1   D1
8   A5  B5   K1   K0   C1   D1
10  A6  B6   K2   K1  NaN  NaN

问题是 C 列和 D 列包含相同的值,这是因为默认的 keep=First 行为。我想改变这种行为,这样我就可以低于预期的 Dataframe。

编辑:

如果左侧 Dataframe 的 key1 和 key2 在右侧 Dataframe 的 key1 和 key2 中匹配,则将 C 和 D 列附加到该行,如果 C 和 D 列已经附加到同一行,则将 C 和 D 保留为 Nan。

预期输出:

     A   B key1 key2    C    D
0   A0  B0   K0   K0   C0   D0
1   A1  B1   K0   K1  NaN  NaN
2   A2  B2   K1   K0   C1   D1
3   A3  B3   K1   K0   C2   D2
4   A4  B4   K1   K0   NaN  Nan
5   A5  B5   K1   K0   NaN  Nan
6   A6  B6   K2   K1  NaN  NaN

【问题讨论】:

df1 有四行 K1K0df2 有两个这样的行。您的预期结果由与df1 匹配的四个这样的行组成,我们在df1 的可用行中交替显示。如果df1 中有 3 个这样的行,df2 有两个这样的行会发生什么 @piRSquared- 实际上列 C 和 D 对我来说很重要,所以我想从列 C 和 D 中获取所有条目,这些条目对于特定匹配是唯一的。在这种情况下(df1 情况下为 3 行),前 2 行应采用 C1 和 D1,第三行应采用 C2 和 D2。 @piRSquared- 请参阅编辑。我们可以这样做吗? 【参考方案1】:

很遗憾,您的问题并没有描述您想要实现的目标,因为它可能对遇到类似问题的任何人都有用。

确实,您希望获得重复合并键的排序合并

进行的合乎逻辑的方法是add a sequence number 以使合并的多个键唯一。然后是一个简单的合并。

left['Order'] = left.groupby(['key1','key2']).cumcount()
right['Order'] = right.groupby(['key1','key2']).cumcount()

result = left.merge(right, how='left', 
                    on=['key1','key2','Order']).drop('Order',axis=1)

【讨论】:

以上是关于当两个数据框都包含重复键时,如何将两个熊猫数据框与左连接合并?的主要内容,如果未能解决你的问题,请参考以下文章

如何合并两个熊猫数据框[重复]

当字符串包含 PHP 中的重复键时,如何将字符串转换为关联数组? [复制]

将具有两个日期列的一个数据框与另一个具有两个日期列的数据框合并

合并两个数据框而不重复熊猫

如何基于每个数据框中具有不同名称的两列将两个数据框与 dplyr 连接起来? [复制]

将两个熊猫数据框组合在一起Python [重复]