R 返回最后一次出现id的行
我有以下格式的日志条目表:R 返回最后一次出现id的行,r,R,我有以下格式的日志条目表: timestamp,id,enabled 2014-11-07 17:16:38,1,TRUE 2014-11-07 17:44:30,2,TRUE 2014-11-07 18:07:13,2,FALSE 2014-11-07 18:11:48,1,TRUE 我想返回每个特定id出现的最后一行。因此,在上述情况下,输出为: 2014-11-07 18:07:13,2,FALSE 2014-11-07 18:11:48,1,TRUE 在R中如何才能做到这一点?有很多
timestamp,id,enabled
2014-11-07 17:16:38,1,TRUE
2014-11-07 17:44:30,2,TRUE
2014-11-07 18:07:13,2,FALSE
2014-11-07 18:11:48,1,TRUE
我想返回每个特定id出现的最后一行。因此,在上述情况下,输出为:
2014-11-07 18:07:13,2,FALSE
2014-11-07 18:11:48,1,TRUE
在R中如何才能做到这一点?有很多方法可以做到这一点。这里有一个使用
dplyr
包的方法,假设您的数据帧被称为dat
:
library(dplyr)
dat %>% group_by(id) %>%
slice(length(id)) # This selects the last row for a given ID
date id enabled
1 2014-11-07 18:11:48 1 TRUE
2 2014-11-07 18:07:13 2 FALSE
如果要根据某个排序变量选择最后一行,如本例中的date
,则在切片之前先按日期排序:
# First, convert date string to date format
library(lubridate)
dat$date = ymd_hms(dat$date)
dat %>% group_by(id) %>%
arrange(date) %>%
slice(length(id))
更新:或者,如果您曾经使用@BenBolker编写高尔夫代码,并且需要从分数中删除几个字符:
dat %>% group_by(id) %>%
slice(n())
只需两个解决方案,无需加载任何包
x <- read.csv(textConnection("timestamp,id,enabled
2014-11-07 17:16:38,1,TRUE
2014-11-07 17:44:30,2,TRUE
2014-11-07 18:07:13,2,FALSE
2014-11-07 18:11:48,1,TRUE"),header = TRUE,stringsAsFactors =FALSE)
# Solution 1
aggregate(x,by=list(x$id),FUN=function(x){tail(x,1)})
# Solution 2
data.frame(do.call('rbind',as.list(by(x,x$id,tail,1))),
stringsAsFactors = FALSE)
x在plyr
中的解决方案特别紧凑(尽管可能比dplyr
慢):
tail(1)
是否可以代替slice(length(id))
?tail
似乎不支持分组变量,所以您需要将其包装在do
中:dat%>%group\u by(id)%>%do(tail(,1))
仍然将代码从17个字符减少到13个字符(我们在打高尔夫,对吧?)嘿嘿,嘿嘿。打得好。
library("plyr")
ddply(dat,"id",tail,1)