计算R中两个事件(给定日期和时间)之间的时间差

时间:2015-01-22 14:30:06

标签: r posixct strptime

我目前正在努力解决有关计算两个事件之间时差的初学者问题。

我想考虑一个由日期和时间(一列中的两个值)组成的列,并使用相同 ID(A)计算上一行/下一行值的时差或者在这个例子中B。)

ID = c("A", "A", "B", "B")
time = c("08.09.2014 10:34","12.09.2014 09:33","13.08.2014 15:52","11.09.2014 02:30")
d = data.frame(ID,time)

我想要的输出格式为小时:分钟

time difference = c("94:59","94:59","682:38","682:38")

格式Days:Hours:Minutes或任何类似的格式也可以使用,只要它可以方便地实现。我对输出的格式很灵活,上面只是我想到的一个想法。

对于每个单独的ID,我总是有两行(在示例中为2xA和2xB)。我不知道如何避免重复差异。

我之前尝试过一些例子,我在stackoverflow上找到了它们。他们中的大多数使用POSIXtstrptime。但是,我没有设法将这些想法应用到我的数据集中。

3 个答案:

答案 0 :(得分:2)

我尝试使用dplyr

library(dplyr)
d %>%
  mutate(time = as.POSIXct(time, format = "%d.%m.%Y %H:%M")) %>%
  group_by(ID) %>%
  mutate(diff = paste0(gsub("[.].*", "", diff(time)*24), ":",
                       round(as.numeric(gsub(".*[.]", ".", diff(time)*24))*60)))


# Source: local data frame [4 x 3]
# Groups: ID
# 
#   ID                time   diff
# 1  A 2014-09-08 10:34:00  94:59
# 2  A 2014-09-12 09:33:00  94:59
# 3  B 2014-08-13 15:52:00 682:38
# 4  B 2014-09-11 02:30:00 682:38

答案 1 :(得分:1)

一个非常(对我来说)hack-ish基础解决方案:

ID <- c("A", "A", "B", "B")
time <- c("08.09.2014 10:34", "12.09.2014 09:33", "13.08.2014 15:52","11.09.2014 02:30")
d <- data.frame(ID, time)

d$time <- as.POSIXct(d$time, format="%d.%m.%Y %H:%M")

unlist(unname(lapply(split(d, d$ID), function(d) {
  sapply(abs(diff(c(d$time[2], d$time))), function(x) {
    sprintf("%s:%s", round(((x*24)%/%1)), round(((x*24)%%1 *60)))
  }) 
})))

## [1] "94:59"  "94:59"  "682:38" "682:38"

我必须相信这个功能已经存在于某个地方了。

答案 2 :(得分:0)

类似于David和hrmbrmstr的尝试,我发现使用difftime的此解决方案正常工作

我使用了在stackoverflow上找到的rowhift脚本

rowShift <- function(x, shiftLen = 1L) {
   r <- (1L + shiftLen):(length(x) + shiftLen)
   r[r<1] <- NA
   return(x[r])
}
d$time.c <- as.POSIXct(d$time, format = "%d.%m.%Y %H:%M")
d$time.prev <- rowShift(d$time.c,-1)
d$diff <- difftime(d$time.c,d$time.prev, units="hours")

d$diff的每一行都有结果中的正/负值。我确实删除了所有具有负值的行,并且每个ID都有第一次和最后一次的差异。