【问题标题】:Calculate time duration in seconds of single Date column, while group_by ID in R计算单个日期列的持续时间(以秒为单位),而 R 中的 group_by ID
【发布时间】:2020-04-22 20:05:59
【问题描述】:

R 有没有办法按 ID 分组,识别时间“中断”,将其设置为 0,然后计算时间差?

例如:

                ID               TIME              
                A                12/18/2019 4:45:10 AM
                A                12/18/2019 4:45:11 AM
                A                12/18/2019 9:06:59 PM               
                B                12/18/2019 4:14:13 AM
                B                12/18/2019 4:14:14 AM

有人知道找到 A 持续时间的方法吗?请注意,这不是 difftime 问题。我在凌晨 4:45:10 执行了某项活动,然后在凌晨 4:45:11 再次执行。然后我停止了这项活动,并在晚上 9 点 06 分恢复。是否有代码可以准确地对 ID 进行分组,然后以秒为单位计算时间差,同时将时间间隔设置为“0”以避免不准确的值?

这不是正确的解决方案。

                       diff<- data %>%
                       mutate(diff = difftime(as.POSIXct(Endtime, format = "%m/%d/%Y %I:%M:%S %p"), 
                       as.POSIXct(Starttime, format = "%m/%d/%Y %I:%M:%S %p"), units = "secs"))

结果:

                ID               TIME                         Duration   
                A                12/18/2019 4:45:10 AM        1 sec
                A                12/18/2019 4:45:11 AM        
                A                12/18/2019 9:06:59 PM        0 sec                    
                B                12/18/2019 4:14:13 AM        1 sec
                B                12/18/2019 4:14:14 AM

非常感谢任何帮助。 我会继续研究这个。谢谢

【问题讨论】:

  • 你能在帖子中显示预期的输出吗
  • 您好,我已经添加了预期的输出。我想按 ID 分组,配对相似的日期时间并计算它们的持续时间。此 ID 中任何不同小时或分钟的日期时间都将被分配值 0。
  • 如果超过 1 秒,你是否在进行剪切
  • 如果小时和分钟与其上方的行不连续,我将值分配给 0

标签: r loops time dplyr


【解决方案1】:

我们使用lubridate中的mdy_hms将'TIME'转换为Datetime类,按'ID'分组,通过使用@987654323获取相邻元素之间'TIME'的差异来检查'TIME'中的连续元素@(指定unit),使用cumsum创建一个数字索引,并将其添加为分组列以在'TIME'元素之间创建difference作为新列'Duration'

library(dplyr)
library(lubridate)
df1 %>% 
  mutate(TIME = mdy_hms(TIME)) %>%
  group_by(ID) %>%  
  group_by(grp = cumsum(as.numeric(difftime(TIME,
     lag(TIME, default = first(TIME)), TIME, unit = 'sec')) > 1), add = TRUE) %>% 
  mutate(Duration = if(n() == 1) NA_real_ else as.numeric(c(diff(TIME), 0))) %>%
  ungroup %>%
  select(-grp)
# A tibble: 5 x 3
#  ID    TIME                Duration
#  <chr> <dttm>                 <dbl>
#1 A     2019-12-18 04:45:10        1
#2 A     2019-12-18 04:45:11        0
#3 A     2019-12-18 21:06:59       NA
#4 B     2019-12-18 04:14:13        1
#5 B     2019-12-18 04:14:14        0

数据

df1 <- structure(list(ID = c("A", "A", "A", "B", "B"), TIME = c("12/18/2019 4:45:10 AM", 
"12/18/2019 4:45:11 AM", "12/18/2019 9:06:59 PM", "12/18/2019 4:14:13 AM", 
"12/18/2019 4:14:14 AM")), class = "data.frame", row.names = c(NA, 
-5L))

【讨论】:

  • 你好 Akrun,我不断收到:意外的特殊 %>% 我需要格式吗?
  • 我认为这行得通,我会彻底检查它。由于我还在学习,你能解释一下代码在做什么吗?
  • @TanishaHudson。我用描述更新了帖子
  • @TanishaHudson。是的,您可以将其设置为任何值。我使用了NA,因为在您的预期中,它更像是一个空白"",它是字符,它会转换为字符类
  • @TanishaHudson 是的,我使用了NA_real_,因为 diff 输出的类型是数字
猜你喜欢
  • 1970-01-01
  • 2016-06-03
  • 2017-06-15
  • 2023-02-05
  • 2014-02-27
  • 1970-01-01
  • 1970-01-01
  • 1970-01-01
  • 2017-05-30
相关资源
最近更新 更多