【问题标题】:Pandas - Merge two dataframes with different number of rowsPandas - 合并具有不同行数的两个数据框
【发布时间】:2017-05-09 06:22:13
【问题描述】:

我有以下两个数据框:

df:

              value
period
2000-01-01    100
2000-04-01    200
2000-07-01    300
2000-10-01    400
2001-01-01    500

df1:

              value
period
2000-07-01    350
2000-10-01    450
2001-01-01    550
2001-04-01    600
2001-07-01    700

这是所需的输出:

df:

              value
period
2000-01-01    100
2000-04-01    200
2000-07-01    350
2000-10-01    450
2001-01-01    550
2001-04-01    600
2001-07-01    700

我在 df1 和 df2 上都有 set_index(['period'])。在创建新列后,我还尝试了一些东西,包括 concat 和 where 语句,但没有按预期工作。我的第一个数据框是主要的。第二种是更新。它应该替换第一个中的相应值,并同时添加新记录(如果有的话)。

我该怎么做?

【问题讨论】:

  • 它看起来像一个简单的连接。您能否详细说明“没有按预期工作”?
  • 这不起作用:pd.concat([df, df1], axis=0)
  • @AlIvon 随意对已接受的答案以及您认为有用的任何其他答案进行投票。

标签: python pandas


【解决方案1】:

您可以使用combine_first,如果某个索引的dtypeobject,则转换to_datetime,如果df1.index 始终在df.index 中,则效果很好:

print (df.index.dtype)
object

print (df1.index.dtype)
object

df.index = pd.to_datetime(df.index)
df1.index = pd.to_datetime(df1.index)

df = df1.combine_first(df)
#if necessary int columns
#df = df1.combine_first(df).astype(int)
print (df)
            value
period           
2000-01-01  100.0
2000-04-01  200.0
2000-07-01  350.0
2000-10-01  450.0
2001-01-01  550.0
2001-04-01  600.0
2001-07-01  700.0

如果不是,则必须先通过intersection过滤:

df = df1.loc[df1.index.intersection(df.index)].combine_first(df)

numpy.setdiff1dconcat 的另一种解决方案

df = pd.concat([df.loc[np.setdiff1d(df.index, df1.index)], df1])
print (df)
            value
period           
2000-01-01    100
2000-04-01    200
2000-07-01    350
2000-10-01    450
2001-01-01    550
2001-04-01    600
2001-07-01    700

【讨论】:

  • combine_first 完成了这项工作。谢谢。
  • 很高兴能帮到你!美好的一天!
【解决方案2】:

这是你想要的吗?

In [151]: pd.concat([df1, df.loc[df.index.difference(df1.index)]]).sort_index()
Out[151]:
            value
period
2000-01-01    100
2000-04-01    200
2000-07-01    350
2000-10-01    450
2001-01-01    550
2001-04-01    600
2001-07-01    700

PS 确保两个索引的 dtype 相同 - 最好使用 pd.to_datetime() 方法将它们转换为 datetime dtype

【讨论】:

  • TypeError: unorderable types: datetime.date() > str()。删除 .sort_index() 时不会出现最后一个结果。 2001-07-01 不见了。
  • @AlIvon,您的索引之一具有object dtype,因此出现此错误
【解决方案3】:

appenddrop_duplicates 的另一个选项

d1 = df1.append(df)
d1[~d1.index.duplicated()]

            value
period           
2000-07-01    350
2000-10-01    450
2001-01-01    550
2001-04-01    600
2001-07-01    700
2000-01-01    100
2000-04-01    200

【讨论】:

    【解决方案4】:

    我使用 pd.concat() 函数连接数据帧,然后删除重复项以获得结果。

    df_con = pd.concat([df, df1])
    df_con.drop_duplicates(subset="period",keep="last",inplace=True)
    print(df_con)
    
           period  value
    0  2000-01-01    100
    1  2000-04-01    200
    0  2000-07-01    350
    1  2000-10-01    450
    2  2001-01-01    550
    3  2001-04-01    600
    4  2001-07-01    700
    

    要将“句点”设置为索引,只需设置索引,

    print(df_con.set_index("period"))
    
                value
    period           
    2000-01-01    100
    2000-04-01    200
    2000-07-01    350
    2000-10-01    450
    2001-01-01    550
    2001-04-01    600
    2001-07-01    700
    

    【讨论】:

      猜你喜欢
      • 2015-03-21
      • 2019-01-21
      • 1970-01-01
      • 2019-12-16
      • 1970-01-01
      • 2023-02-08
      • 1970-01-01
      • 2018-08-06
      • 1970-01-01
      相关资源
      最近更新 更多