дата-время сегрегации на почасовой основе в R - PullRequest
0 голосов
/ 05 февраля 2020

Я использую нижеупомянутый фрейм данных в R:

ID          Datetime                Value
T-1         2020-01-01 15:12:14     10
T-2         2020-01-01 00:12:10     20
T-3         2020-01-01 03:11:11     25
T-4         2020-01-01 14:01:01     20
T-5         2020-01-01 18:07:11     10
T-6         2020-01-01 20:10:09     15
T-7         2020-01-01 15:45:23     15

Используя вышеупомянутый фрейм данных, я хочу разделить дату и время на почасовой основе. Для этого я использую следующий код:

library(tidyverse)

DF$bins <- cut(lubridate::hour(DF$Datetime), c(-1, 0:24 - 0.01))

levels(DF$bins) <- c("00:00 to 00:59",  "00:01 to 01:59",   "00:02 to 02:59",   "00:03 to 03:59",   "00:04 to 04:59",   "00:05 to 05:59",   
                     "00:06 to 06:59",  "00:07 to 07:59",   "00:08 to 08:59",   "00:09 to 09:59",   "00:10 to 10:59",   "00:11 to 11:59",
                     "00:12 to 12:59",  "00:13 to 13:59",   "00:14 to 14:59",   "00:15 to 15:59",   "00:16 to 16:59",   "00:17 to 17:59",
                     "00:18 to 18:59",  "00:19 to 19:59",   "00:20 to 20:59",   "00:21 to 21:59",   "00:22 to 22:59",   "00:23 to 23:59")



newDF <- DF %>% 
  dplyr::group_by(bins, .drop = FALSE) %>% 
  dplyr::summarise(Count = length(Value), Total = sum(Value))

Final<-newDF %>% 
  dplyr::summarise(bins = "January", Count = sum(Count), Total = sum(Total)) %>% bind_rows(newDF)

Final[,c(2,3)]<-sapply(Final[,c(2,3)], function(x) scales::comma(x))

на levels(DF$bins)<- Я получаю ошибку Error in уровни <-. Фактор <code>( tmp , value = c("00:00 to 00:59", "00:01 to 01:59", : number of levels differs

Как сохранить нижеупомянутую сегрегацию stati c и соответствующим образом собрать числа

"00:00 to 00:59",   "00:01 to 01:59",   "00:02 to 02:59",   "00:03 to 03:59",   "00:04 to 04:59",   "00:05 to 05:59",   "00:06 to 06:59",   "00:07 to 07:59",   "00:08 to 08:59",   "00:09 to 09:59",   "00:10 to 10:59",   "00:11 to 11:59","00:12 to 12:59",  "00:13 to 13:59",   "00:14 to 14:59",   "00:15 to 15:59",   "00:16 to 16:59",   "00:17 to 17:59","00:18 to 18:59",  "00:19 to 19:59",   "00:20 to 20:59",   "00:21 to 21:59",   "00:22 to 22:59",   "00:23 to 23:59"

Ожидаемый результат:

Month                   Count              Sum
Jan-20                   7                 115
12:00 AM to 05:00 AM     2                 45
06:00 AM to 12:00 PM     0                 0
12:00 PM to 03:00 PM     1                 20
03:00 PM to 08:00 PM     3                 35
08:00 PM to 12:00 AM     1                 15

1 Ответ

1 голос
/ 05 февраля 2020

Мы можем использовать floor_date / ceiling_date из lubridate для создания часовых перерывов, создать столбец группировки (bins) на основе нашего требования, используя sprintf, а затем использовать этот столбец для вычисления того, что мы хотим для каждая группа.

library(dplyr)
library(lubridate)

df %>%
  mutate(bins = floor_date(Datetime, "hour"), 
         hour = hour(bins), 
         bins = paste0(sprintf("%02d:00 :", hour), sprintf(" %02d:59", hour))) %>%
  group_by(bins) %>%
  summarise(sum = sum(Value))

# A tibble: 6 x 2
#  bins            sum
#  <chr>         <int>
#1 00:00 : 00:59    20
#2 03:00 : 03:59    25
#3 14:00 : 14:59    20
#4 15:00 : 15:59    25
#5 18:00 : 18:59    10
#6 20:00 : 20:59    15

Для обновленного условия мы можем сделать

df %>%
  mutate(hour = hour(Datetime),
         gr = case_when(hour >= 0 & hour < 6 ~ "12:00 AM to 06:00 AM", 
                        hour >= 6 & hour < 12 ~ "06:00 AM to 12:00 PM",
                        hour >= 12 & hour < 15 ~ "12:00 PM to 03:00 PM",
                        hour >= 15 & hour < 20 ~ "03:00 PM to 08:00 PM",
                        TRUE ~ "08:00 PM to 12:00 AM"),
         month_year = format(Datetime, "%Y-%m"),
         bins = factor(gr, levels = c("12:00 AM to 06:00 AM", "06:00 AM to 12:00 PM", 
                                    "12:00 PM to 03:00 PM", "03:00 PM to 08:00 PM", 
                                    "08:00 PM to 12:00 AM"))) %>%
  group_by(month_year, bins, .drop = FALSE) %>%
  summarise(sum = n())

# month_year bins                   sum
#  <chr>      <fct>                <int>
#1 2020-01    12:00 AM to 06:00 AM     2
#2 2020-01    06:00 AM to 12:00 PM     0
#3 2020-01    12:00 PM to 03:00 PM     1
#4 2020-01    03:00 PM to 08:00 PM     3
#5 2020-01    08:00 PM to 12:00 AM     1

data

df <- structure(list(ID = structure(1:7, .Label = c("T-1", "T-2", "T-3", 
"T-4", "T-5", "T-6", "T-7"), class = "factor"), Datetime = structure(c(1577891534, 
1577837530, 1577848271, 1577887261, 1577902031, 1577909409, 1577893523
), class = c("POSIXct", "POSIXt"), tzone = "UTC"), Value = c(10L, 
20L, 25L, 20L, 10L, 15L, 15L)), row.names = c(NA, -7L), class = "data.frame")
Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...