Calculate time difference (difftime) between columns of different rows

梦想的初衷 提交于 2019-12-06 06:47:42

Here's a possible solution using data.table

library(data.table) # v 1.9.5+
setDT(Data)[, idletime := difftime(Start, shift(End), units = "mins"), by = owner]
#    job owner               Start                 End       idletime
# 1:   1 name1 2015-01-01 15:00:00 2015-01-01 15:11:11        NA mins
# 2:   2 name2 2015-01-01 15:01:00 2015-01-01 15:17:21        NA mins
# 3:   3 name1 2015-01-01 15:13:00 2015-01-01 15:17:00  1.816667 mins
# 4:   4 name1 2015-01-01 15:20:00 2015-01-01 15:31:21  3.000000 mins
# 5:   5 name2 2015-01-01 15:39:02 2015-01-01 15:40:11 21.683333 mins

Or using dplyr

library(dplyr)
Data %>%
  group_by(owner) %>%
  mutate(idletime = difftime(Start, lag(End), units = "mins"))

# Source: local data frame [5 x 5]
# Groups: owner
# 
#   job owner               Start                 End       idletime
# 1   1 name1 2015-01-01 15:00:00 2015-01-01 15:11:11        NA mins
# 2   2 name2 2015-01-01 15:01:00 2015-01-01 15:17:21        NA mins
# 3   3 name1 2015-01-01 15:13:00 2015-01-01 15:17:00  1.816667 mins
# 4   4 name1 2015-01-01 15:20:00 2015-01-01 15:31:21  3.000000 mins
# 5   5 name2 2015-01-01 15:39:02 2015-01-01 15:40:11 21.683333 mins

If we are using base R, ave would be one option. We get the lag of the 'End' grouped by 'owner' using ave, use that as the second argument in difftime to create the 'idtime'.

Data$idtime <- with(Data, difftime(Start, ave(End, owner,FUN=lag), units='mins'))

Data
#  job owner               Start                 End         idtime
#1   1 name1 2015-01-01 15:00:00 2015-01-01 15:11:11        NA mins
#2   2 name2 2015-01-01 15:01:00 2015-01-01 15:17:21        NA mins
#3   3 name1 2015-01-01 15:13:00 2015-01-01 15:17:00  1.816667 mins
#4   4 name1 2015-01-01 15:20:00 2015-01-01 15:31:21  3.000000 mins
#5   5 name2 2015-01-01 15:39:02 2015-01-01 15:40:11 21.683333 mins

NOTE: I named the column name as 'idtime' to keep the code in a single line :-)

library(dplyr)


Data <- data.frame(
  job = c(1, 2, 3, 4, 5),
  owner = c("name1", "name2", "name1", "name1", "name2"),
  Start = as.POSIXct(c("2015-01-01 15:00:00", "2015-01-01 15:01:00", "2015-01-01 15:13:00", "2015-01-01 15:20:00", "2015-01-01 15:39:02"), format="%Y-%m-%d %H:%M:%S"),
  End =   as.POSIXct(c("2015-01-01 15:11:11", "2015-01-01 15:17:21", "2015-01-01 15:17:00", "2015-01-01 15:31:21", "2015-01-01 15:40:11"), format="%Y-%m-%d %H:%M:%S")
)


Data %>% 
  group_by(owner) %>% 
  arrange(Start) %>% 
  mutate(lagEnd = lag(End),
         idletime = difftime(Start,lagEnd, units="mins")) %>%
  ungroup %>%
  arrange(job) %>%
  select(job,owner,idletime)

#   job owner        idletime
# 1   1 name1         NA mins
# 2   2 name2         NA mins
# 3   3 name1   1.816667 mins
# 4   4 name1   3.000000 mins
# 5   5 name2  21.683333 mins
易学教程内所有资源均来自网络或用户发布的内容,如有违反法律规定的内容欢迎反馈
该文章没有解决你所遇到的问题?点击提问,说说你的问题,让更多的人一起探讨吧!