我有3个具有不同结构的数据框,其中一个包含2个与其他两个链接的键:
df1 = id1 id2 df2 = id1 a b1 c1 c2 df3 = id2 a b1 b2 c1
1 1 1a 1b1 1c1 1c2 11 11a 11b1 11b2 11c1
11 2 2a 2b1 2c1 2c2 12 12a 12b1 12b2 12c1
12 3 3a 3b1 3c1 3c2 13 13a 13b1 13b2 13c1
13 14 14a 14b1 14b2 14c1
2 21 21a 21b1 21b2 21c1
21 22 22a 22b1 22b2 22c1
22 23 23a 23b1 23b2 23c1
31 31a 31b1 31b2 31c1
然后我将df1
与df2
合并:
df1 = pd.merge(df1, df2, on='id1', how='left')
df1 = id1 id2 a b1 c1 c2
1 1a 1b1 1c1 1c2
11 nan nan nan nan
12 nan nan nan nan
13 nan nan nan nan
2 2a 2b1 2c1 2c2
21 nan nan nan nan
22 nan nan nan nan
但是当我与df3
合并时,我有:
df1 = pd.merge(df1, df3, on='id2', how='left')
df1 = id1 id2 a_x b1_x c1_x c2 a_y b1_y b2 c1_y
1 1a 1b1 1c1 1c2
11 nan nan nan nan 11a 11b1 11b2 11c1
12 nan nan nan nan 12a 12b1 12b2 12c1
13 nan nan nan nan 13a 13b1 13b2 13c1
2 2a 2b1 2c1 2c2
21 nan nan nan nan 21a 21b1 21b2 21c1
22 nan nan nan nan 22a 22b1 22b2 22c1
简而言之,当要合并的数据帧之间有重叠的列时,该方法将创建一个新的带有砜的列。但是,我希望这些值在重合的列中被替换。
我想要得到的是这样的:
df1 = id1 id2 a b1 c1 c2 b2
1 1a 1b1 1c1 1c2
11 11a 11b1 11c1 11b2
12 12a 12b1 12c1 12b2
13 13a 13b1 13c1 13b2
2 2a 2b1 2c1 2c2
21 21a 21b1 21c1 21b2
22 22a 22b1 22c1 22b2
在第二次合并之前,我也尝试过fillna('')
,但结果相同。
答案 0 :(得分:1)
尝试如下
df1 = pd.merge(df1, df3, on='id2', how='left')
df1['a']=df1['a_y'].fillna(df1['a_x'])
df1['b']=df1['b_y'].fillna(df1['b_x'])
df1['c1']=df1['c1_y'].fillna(df1['c1_x'])
答案 1 :(得分:0)
在大熊猫中,这是一个非常困难的问题。我也一直试图处理它。一种选择是为每个单独的合并创建一个单独的数据框,然后将它们合并在一起。我认为这不是“替代方法-y”:
df_m1 = pd.merge(df1, df2, on='id1', how='inner') # note it's an inner merge
df_m2 = pd.merge(df1, df3, on='id2', how='inner')
df1 = pd.concat([df_m1, df_m2])
但是,会有一个问题:如果df1
中有某些行无法与您想要保留的df2
或df3
合并,它们将不会停留在上面的示例中。您必须手动添加它们。在这一点上,如果您可以手动添加具有不在df_m1
或df_m2
中的索引的行,那将是很好的选择,但是问题是合并不能保存索引(请参阅:{ {3}}),这的确使这个问题更加复杂了。
因此您可以将以上内容修改为:
df_m1 = pd.merge(df1, df2, on='id1', how='inner') # note it's an inner merge
df_m2 = pd.merge(df1, df3, on='id2', how='inner')
df1 = pd.concat([df_m1, df_m2, df1[~df1.id1.isin(df2.id1) & ~df1.id2.isin(df3.id2)])
如果有更好的方法来完成最后一部分,那就太好了。如果您还需要合并任意数量的数据帧,则以上内容是可循环的。
编辑:或者,由于通常情况下,当您要合并3个以上的数据框时,将有助于使用索引完成最后一部分,因此您可以执行以下操作:
df1['old_index'] = df1.index # this will let you keep the index
df_m1 = pd.merge(df1, df2, on='id1', how='inner') # note it's an inner merge
df_m2 = pd.merge(df1, df3, on='id2', how='inner')
df_other = df1[~df1.old_index.isin(pd.concat([df_m1, df_m2]).old_index)]
df1 = pd.concat([df_m1, df_m2, df_other])
这将更容易陷入循环。