【问题标题】:How to delete duplicates but keep most recent data in R如何删除重复项但在 R 中保留最新数据
【发布时间】:2016-07-18 21:15:03
【问题描述】:

我有以下两个数据框:

df1 = data.frame(names=c('a','b','c','c','d'),year=c(11,12,13,14,15), Times=c(1,1,3,5,6))
df2 = data.frame(names=c('a','e','e','c','c','d'),year=c(12,12,13,15,16,16), Times=c(2,2,4,6,7,7))

我想知道如何合并上述 df,但只保留最新的 Times,具体取决于年份。它应该是这样的:

Names  Year   Times
a      12     2
b      12     2
c      16     7
d      16     7
e      13     4

【问题讨论】:

    标签: r dataframe merge


    【解决方案1】:

    我猜您并不是要合并这些,而是​​要通过堆叠进行合并。您的问题含糊不清,因为“重复”可能发生在数据帧级别或向量级别。您的示例不会在数据帧级别显示任何重复,但会在矢量级别显示。描述问题的最佳方式是,如果 names 值,您希望每个组中的最后一个(或最大)Times 条目:

    > df1
      names year Times
    1     a   11     1
    2     b   12     1
    3     c   13     3
    4     c   14     5
    5     d   15     6
    > df2
      names year Times
    1     a   12     2
    2     e   12     2
    3     e   13     4
    4     c   15     6
    5     c   16     7
    6     d   16     7
    > dfr <- rbind(df1,df2)
    > dfr <-dfr[order(dfr$Times),]
    > dfr[!duplicated(dfr, fromLast=TRUE) , ]
       names year Times
    1      a   11     1
    2      b   12     1
    6      a   12     2
    7      e   12     2
    3      c   13     3
    8      e   13     4
    4      c   14     5
    5      d   15     6
    9      c   15     6
    10     c   16     7
    11     d   16     7
    
    > dfr[!duplicated(dfr$names, fromLast=TRUE) , ]
       names year Times
    2      b   12     1
    6      a   12     2
    8      e   13     4
    10     c   16     7
    11     d   16     7
    

    【讨论】:

      【解决方案2】:

      这使用基本 R 函数;还有一些更新的包(例如 plyr),许多人认为它们使拆分-应用-组合过程更加直观。

      df <- rbind(df1,  df2)
      do.call(rbind, lapply(split(df, df$names), function(x) x[which.max(x$year), ]))
      
      ##   names year Times
      ## a     a   12     2
      ## b     b   12     1
      ## c     c   16     7
      ## d     d   16     7
      ## e     e   13     4
      

      【讨论】:

      • split+lapply=by - do.call(rbind,by(df, df$names, function(x) x[which.max(x$year), ]))
      【解决方案3】:

      我们也可以使用aggregate:

      df <- rbind(df1,df2)
      aggregate(cbind(df$year,df$Times)~df$names,df,max)
      
        # df$names V1 V2
      # 1        a 12  2
      # 2        b 12  1
      # 3        c 16  7
      # 4        d 16  7
      # 5        e 13  4
      

      【讨论】:

      • 在使用公式界面的时候不需要一直引用df,也就是说你甚至可以做-aggregate(cbind(year,Times) ~ names, data=rbind(df1,df2), FUN=max)
      【解决方案4】:

      如果您想查看data.table 解决方案,

      # load library
      library(data.table)
      # bind by row and convert to data.table (by reference)
      df <- setDT(rbind(df1, df2))
      # get the result
      df[order(names, year), .SD[.N], by=.(names)]
      

      输出如下:

         names year Times
      1:     a   12     2
      2:     b   12     1
      3:     c   16     7
      4:     d   16     7
      5:     e   13     4
      

      最后一行按名称和年份对行绑定数据进行排序,然后为每个名称选择最后一个观察值 (.sd[.N])。

      【讨论】:

        猜你喜欢
        • 1970-01-01
        • 1970-01-01
        • 2022-07-19
        • 2019-02-23
        • 2019-09-03
        • 1970-01-01
        • 1970-01-01
        • 2017-02-12
        • 1970-01-01
        相关资源
        最近更新 更多