【问题标题】:(Longitudinal data) Create new variable with last value for each ID(纵向数据)使用每个 ID 的最后一个值创建新变量
【发布时间】:2019-11-18 18:51:17
【问题描述】:

我正在处理具有 ID、时间戳和值的纵向数据集。我想为每个人创建一个新变量,该变量在该人的每一行中保存该人的最后一个时间戳的值。例如,如果我的数据如下所示:

    ID Time Value
    1  1:20  1
    1  2:43  2
    1  1:56  3
    2  1:10  4
    2  1:05  5

我想像这样创建一个新变量 Final_value:

    ID Time Value Final_value
    1  1:20  1    2
    1  2:43  2    2
    1  1:56  3    2
    2  1:10  4    4
    2  1:05  5    4

我更喜欢使用 R 的内置方法。也许有一种方法可以使用“ave”函数来做到这一点?

【问题讨论】:

    标签: r longitudinal


    【解决方案1】:

    这是dplyr 的选项。按“ID”分组,使用hm 从lubridate 将“时间”转换为时间类,获取最大值的索引(which.max)并根据该索引子集“值”

    library(dplyr)
    library(lubridate)
    df1 %>%
       group_by(ID) %>%
       mutate(Final_value = Value[which.max(as.numeric(hm(Time)))])
    # A tibble: 5 x 4
    # Groups:   ID [2]
    #     ID Time  Value Final_value
    #  <int> <chr> <int>       <int>
    #1     1 1:20      1           2
    #2     1 2:43      2           2
    #3     1 1:56      3           2
    #4     2 1:10      4           4
    #5     2 1:05      5           4
    

    或者使用base R

    df1$Final_value <- with(df1, Value[as.logical(ave(as.numeric(as.POSIXct(Time, 
               format = '%H:%M')),
          ID, FUN = function(x) x== max(x)))][ID])
    

    或者另一种选择是order基于'时间'和'ID'的数据,然后用ave得到last值

    i1 <- with(df1, order(ID, as.POSIXct(TIme, format = '%H:%M')))
    with(df1[i1,], ave(Value, ID, FUN = function(x) x[length(x)]))
    

    数据

    df1 <- structure(list(ID = c(1L, 1L, 1L, 2L, 2L), Time = c("1:20", "2:43", 
    "1:56", "1:10", "1:05"), Value = 1:5), class = "data.frame", row.names = c(NA, 
    -5L))
    

    【讨论】:

      【解决方案2】:

      这里是data.table的thinhs方式

      library( data.table )
      #make your data (dt) a data.table
      setDT( dt )
      #set Time as a  iTime
      dt[, Time := as.ITime( Time )]
      #get the value of the max Time, by ID
      dt[, Final_value :=  , by = .( ID ) ]
      #perform an update join, where you join 
      #  the maximum Value by ID on dt itself
      dt[ dt[dt[, .I[Time == max(Time)], by = ID]$V1], 
          Final_value := i.Value, 
          on = .(ID)]
      
      #    ID     Time Value Final_value
      # 1:  1 01:20:00     1           2
      # 2:  1 02:43:00     2           2
      # 3:  1 01:56:00     3           2
      # 4:  2 01:10:00     4           4
      # 5:  2 01:05:00     5           4
      

      【讨论】:

        猜你喜欢
        • 2015-08-13
        • 2021-04-03
        • 2019-05-13
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2011-06-08
        • 2012-03-13
        • 1970-01-01
        相关资源
        最近更新 更多