r-(纵向数据)为每个ID创建最后一个值的新变量



我正在处理一个包含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"函数来实现这一点?

这里有一个dplyr选项。按"ID"分组,将"Time"从lubridate转换为具有hm的时间类,获得最大值(which.max(的索引,并根据该索引对"Value"进行子集设置

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])

或者另一个选项是根据"时间"one_answers"ID"order数据,然后使用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))

这里是精简的data.table方法

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

相关内容

  • 没有找到相关文章

最新更新