【问题标题】:count new values per date per group每组每个日期计算新值
【发布时间】:2019-08-13 16:10:30
【问题描述】:

假设我有以下数据集

Date      Group    Value
01-01-19  A        X
01-01-19  A        Y
01-01-19  A        Z
02-01-19  A        X
02-01-19  A        Y
02-01-19  A        Z
02-01-19  A        W
01-01-19  B        X
01-01-19  B        Y
01-01-19  B        Z
02-01-19  B        X
02-01-19  B        X
02-01-19  B        Z
02-01-19  B        V

所以有两个组和两个日期。我想查看每个组和每个日期哪些值是新的。

生成的数据框应如下所示

group    date      new_values
A        01-01-19  3 
A        02-01-19  1
B        01-01-19  3
B        02-01-19  1  

最终,我只计算了每组每个日期的值数并取了差值。但这并没有考虑自上一个日期以来已经消失的值。我不知道该怎么做。或许data.table 包可以带来释放

【问题讨论】:

    标签: r dplyr data.table aggregation


    【解决方案1】:

    rowid 函数计算列组合的出现次数,从 1 开始:

    library(data.table)
    setDT(DT)
    
    DT[, new := rowid(Group, Value) == 1L]
    DT[, .(n_new = sum(new)), by=.(Group, Date)]
    #    Group     Date n_new
    # 1:     A 01-01-19     3
    # 2:     A 02-01-19     1
    # 3:     B 01-01-19     3
    # 4:     B 02-01-19     1
    

    【讨论】:

      【解决方案2】:

      一种可能性:

      library(dplyr)
      
      df %>%
        arrange(Date = as.Date(Date, "%d-%m-%y")) %>%
        group_by(Group, Value) %>%
        mutate(New = row_number()) %>%
        group_by(Group, Date) %>%
        summarise(New = sum(New == 1))
      

      输出:

      # A tibble: 4 x 3
      # Groups:   Group [2]
        Group Date       New
        <fct> <fct>    <int>
      1 A     01-01-19     3
      2 A     02-01-19     1
      3 B     01-01-19     3
      4 B     02-01-19     1
      

      以上假设您的日期格式为day-month-year;如果不是这种情况,您只需将"%d-%m-%y" 更改为"%m-%d-%y"

      【讨论】:

        【解决方案3】:

        使用dplyr,我们可以首先使用group_byGroup 并创建一个列(orig),如果它在组中第一次出现,则该列将是TRUE。然后我们group_byGroupDate统计这些原始值的个数。

        library(dplyr)
        
        df %>%
          group_by(Group) %>%
          mutate(orig = !duplicated(Value)) %>%
          group_by(Group, Date) %>%
          summarise(new_values = sum(orig))
        
        #  Group     Date     new_values
        #   <fct> <fct>         <int>
        #1   A     01-01-19          3
        #2   A     02-01-19          1
        #3   B     01-01-19          3
        #4   B     02-01-19          1
        

        【讨论】:

          【解决方案4】:
          library(data.table)
          
          dt <- data.table(read.table(text="
          01-01-19,A,X
          01-01-19,A,Y
          01-01-19,A,Z
          02-01-19,A,X
          02-01-19,A,Y
          02-01-19,A,Z
          02-01-19,A,W
          01-01-19,B,X
          01-01-19,B,Y
          01-01-19,B,Z
          02-01-19,B,X
          02-01-19,B,X
          02-01-19,B,Z
          02-01-19,B,V
          ",sep=",",strip.white = TRUE))
          
          setnames(dt,c("date","group","value"))
          

          一种解决方案是按组查找唯一值。然后按组和日期对唯一值求和。

          ##     > dt[,dup:=!duplicated(value),.(group)][,sum(dup),.(group,date)]
          ## group     date V1
          ## 1:     A 01-01-19  3
          ## 2:     A 02-01-19  1
          ## 3:     B 01-01-19  3
          ## 4:     B 02-01-19  1
          

          【讨论】:

            猜你喜欢
            • 1970-01-01
            • 2015-10-17
            • 1970-01-01
            • 2016-10-14
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            • 1970-01-01
            相关资源
            最近更新 更多