Объединить перекрывающиеся периоды времени с миллисекундами в R - PullRequest
0 голосов
/ 20 февраля 2020

Я пытаюсь найти способ слияния перекрывающихся интервалов времени, которые могут иметь дело с миллисекундами.

Здесь были опубликованы три возможных варианта: Как сгладить / объединить перекрывающиеся периоды времени

Однако мне не нужно группировать по идентификатору, поэтому я нахожу методы dplyr и data.table сбивающими с толку (я не уверен, могут ли они работать с миллисекундами, так как я не могу заставить их работать).

Мне удалось заставить работать решение IRanges, но оно конвертирует POSIXct объекты в as.numeric целые числа для вычисления перекрытий. Итак, я предполагаю, что именно поэтому миллисекунды отсутствуют в выводе?

Отсутствие миллисекунд не является проблемой отображения, так как при вычитании результирующего времени начала и конца я получаю целое число результаты в секундах.

Вот пример моих данных:

start <- c("2019-07-15 21:32:43.565",
           "2019-07-15 21:32:43.634",
           "2019-07-15 21:32:54.301",
           "2019-07-15 21:34:08.506",
           "2019-07-15 21:34:09.957")

end <- c("2019-07-15 21:32:48.445",
         "2019-07-15 21:32:49.045",
         "2019-07-15 21:32:54.801",
         "2019-07-15 21:34:10.111",
         "2019-07-15 21:34:10.236")

df <- data.frame(start, end)

Вывод, полученный из решения IRanges:

                start                 end
1 2019-07-15 21:32:43 2019-07-15 21:32:49
2 2019-07-15 21:32:54 2019-07-15 21:32:54
3 2019-07-15 21:34:08 2019-07-15 21:34:10

И желаемый результат :

                    start                     end
1 2019-07-15 21:32:43.565 2019-07-15 21:32:49.045
2 2019-07-15 21:32:54.301 2019-07-15 21:32:54.801
3 2019-07-15 21:34:08.506 2019-07-15 21:34:10.236

Предложения будут очень признательны!

1 Ответ

0 голосов
/ 20 февраля 2020

Я обнаружил, что довольно просто сохранить миллисекунды, если вы используете формат POSIXlt. Хотя существуют более быстрые способы вычисления перекрытия, для большинства целей достаточно просто просто l oop через фрейм данных.

Вот воспроизводимый пример.

start <- c("2019-07-15 21:32:43.565",
           "2019-07-15 21:32:43.634",
           "2019-07-15 21:32:54.301",
           "2019-07-15 21:34:08.506",
           "2019-07-15 21:34:09.957")

end <- c("2019-07-15 21:32:48.445",
         "2019-07-15 21:32:49.045",
         "2019-07-15 21:32:54.801",
         "2019-07-15 21:34:10.111",
         "2019-07-15 21:34:10.236")

df    <- data.frame(start = as.POSIXlt(start), end = as.POSIXlt(end))

i <- 1

df <- data.frame(start = as.POSIXlt(start), end = as.POSIXlt(end))

while(i < nrow(df))
{
  overlaps <- which(df$start < df$end[i] & df$end > df$start[i])
  if(length(overlaps) > 1)
  {
    df$end[i] <- max(df$end[overlaps])
    df <- df[-overlaps[-which(overlaps == i)], ]
    i <- i - 1
  }
  i <- i + 1
}

Так что теперь наш фрейм данных не имеет перекрытий:

df
#>                 start                 end
#> 1 2019-07-15 21:32:43 2019-07-15 21:32:49
#> 3 2019-07-15 21:32:54 2019-07-15 21:32:54
#> 4 2019-07-15 21:34:08 2019-07-15 21:34:10

Хотя кажется, что мы потеряли миллисекунды, это просто проблема отображения, как мы можем показать по делаем это:

df$end - df$start
#> Time differences in secs
#> [1] 5.48 0.50 1.73

as.numeric(df$end - df$start)
#> [1] 5.48 0.50 1.73

Создано в 2020-02-20 пакетом представить (v0.3.0)

...