• 1000 Вот фиктивный фрейм данных, аналогичный тому, с чем я работаю:
library(ids)#for generating the UserID variable
library(wakefield)#for generating the Status variable
library(dplyr)
set.seed(123)
UserID<-random_id(n=10, bytes = 5)
DateTime<-seq.POSIXt(from = as.POSIXct("2020-08-01 01:00:00", tz = Sys.timezone()), length.out = 70, by = "15 mins")
df<-cbind(UserID,DateTime)
df<-as.data.frame(df)
df$Status<-r_sample_factor(x = c("Answered", "Abandoned", "Engaged"), n=70)
df$DateTime<-seq.POSIXt(from = as.POSIXct("2020-08-01 01:00:00", tz = Sys.timezone()),
length.out = 70, by = "15 mins")#re-doing this again as it annoyingly converts to numeric each time
df<-df%>%arrange(UserID,DateTime)
head(df)
#UserID DateTime Status
#1 0a5f3a2a8b 2020-08-01 02:00:00 Engaged
#2 0a5f3a2a8b 2020-08-01 04:30:00 Engaged
#3 0a5f3a2a8b 2020-08-01 07:00:00 Engaged
#4 0a5f3a2a8b 2020-08-01 09:30:00 Engaged
#5 0a5f3a2a8b 2020-08-01 12:00:00 Engaged
#6 0a5f3a2a8b 2020-08-01 14:30:00 Abandoned
Я хочу подсчитать количество вызовов по UserID
в течение 5 часов с двумя другими условиями:
- Если в течение 5-часового периода с момента последнего звонка, сделанного пользователем, не было другого звонка, то он считается однократной «попыткой»
- Если у пользователя есть N Вызовы в течение 5-часового периода, пока они не получат ответ «Ответил», тогда это считается «успешной» попыткой. В противном случае он будет считаться «неудачным»
Вот чего я пытаюсь достичь: -
UserId OrigTime LastTime Calls Status Successful
0a5f3a2a8b 2020-08-01 02:00:00 2020-08-01 07:00:00 3 Engaged No
16db61d2bc 2020-08-01 03:15:00 2020-08-01 03:15:00 1 Answered Yes
6355f7700d 2020-08-01 01:00:00 2020-08-01 06:00:00 3 Answered Yes
9b9fab9789 2020-08-01 04:15:00 2020-08-01 09:15:00 3 Answered Yes
...
Итак, OrigTime
- это время их первого звонка в единственная попытка, а LastTime
- время их последнего вызова в рамках той же единственной попытки. Столбец Calls
подсчитывает количество вызовов, совершенных пользователем в рамках этой попытки, Status
- это статус последнего вызова в рамках попытки, а «Успешно» может быть логичным, указывая, был ли отвечен последний вызов в этой попытке или нет. .
Любые указатели в правильном направлении были бы здорово. Я предполагаю, что есть какое-то решение data.table
или dplyr
, но я раньше не делал много такого рода деятельности, поэтому не уверен, с чего начать. Заранее большое спасибо :)
ДОБАВЛЕНИЕ
Я хочу повторно загрузить образец данных, который больше похож на данные, которые я я в настоящее время работаю с; Я работаю с данными журнала вызовов с горячей линии телефона, поэтому я предоставил «историю», чтобы помочь проиллюстрировать, чего я хочу достичь. Я включил еще один пример предполагаемого результата, чтобы прояснить ситуацию.
Справочная информация: каждая строка в df
представляет один звонок, сделанный на горячую линию с помощью UserId; Каждая строка в callattempts
представляет собой попытку (попытка может состоять из множества вызовов) дозвониться до службы.
Вот фрейм фиктивных данных: -
#create mock data frame=====================================
UserId<-c("104b0cfb910f7c9de318c05c3c305be2", "104b0cfb910f7c9de318c05c3c305be2",
"1320319e0b65f95b71ce5650b592039b", "54eca3518ca03ca0ae883ff3aaad79fe",
"73ae725b039b4ca0d3727bb2497a717d", "816194b2aa6ae09dea56876b68bb8244",
"e1bd4a520d490a4151882e0a136d3f28", "e1bd4a520d490a4151882e0a136d3f28",
"e1bd4a520d490a4151882e0a136d3f28", "e1bd4a520d490a4151882e0a136d3f28",
"e1bd4a520d490a4151882e0a136d3f28", "e1bd4a520d490a4151882e0a136d3f28",
"e1bd4a520d490a4151882e0a136d3f28", "e1bd4a520d490a4151882e0a136d3f28",
"e1bd4a520d490a4151882e0a136d3f28", "e1bd4a520d490a4151882e0a136d3f28",
"e1bd4a520d490a4151882e0a136d3f28", "e1bd4a520d490a4151882e0a136d3f28",
"e1bd4a520d490a4151882e0a136d3f28", "eb431db274a6b6d2b2c7e455f4e5780b",
"eb431db274a6b6d2b2c7e455f4e5780b", "eb431db274a6b6d2b2c7e455f4e5780b",
"eb431db274a6b6d2b2c7e455f4e5780b", "eb431db274a6b6d2b2c7e455f4e5780b",
"eb431db274a6b6d2b2c7e455f4e5780b", "eb431db274a6b6d2b2c7e455f4e5780b",
"eb431db274a6b6d2b2c7e455f4e5780b", "eb431db274a6b6d2b2c7e455f4e5780b",
"eb431db274a6b6d2b2c7e455f4e5780b", "eb431db274a6b6d2b2c7e455f4e5780b",
"eb431db274a6b6d2b2c7e455f4e5780b", "eb431db274a6b6d2b2c7e455f4e5780b",
"eb431db274a6b6d2b2c7e455f4e5780b", "eb431db274a6b6d2b2c7e455f4e5780b",
"eb431db274a6b6d2b2c7e455f4e5780b", "eb431db274a6b6d2b2c7e455f4e5780b",
"eb431db274a6b6d2b2c7e455f4e5780b", "eb431db274a6b6d2b2c7e455f4e5780b",
"eb431db274a6b6d2b2c7e455f4e5780b", "f4904b5d962d3e8be1dfcc237fbb7e70",
"f4904b5d962d3e8be1dfcc237fbb7e70", "f4904b5d962d3e8be1dfcc237fbb7e70",
"f4904b5d962d3e8be1dfcc237fbb7e70")
DateTime<-structure(c(1546300966, 1546301009, 1546299594, 1546300866, 1546300596,
1546300596, 1546338093, 1546339236, 1546339555, 1546341083, 1546341105,
1546341697, 1546342267, 1546343070, 1546344801, 1546346046, 1546366255,
1546366269, 1546366284, 1546300762, 1546300827, 1546300831, 1546300888,
1546300952, 1546300958, 1546300967, 1546301006, 1546301034, 1546301039,
1546301148, 1546301177, 1546301195, 1546301226, 1546301284, 1546301418,
1546301437, 1546301453, 1546301463, 1546301468, 1546301038, 1546301076,
1546301098, 1546315566), class = c("POSIXct", "POSIXt"), tzone = "UTC")
Status<-c("Abandoned", "Answered", "Answered", "Abandoned", "Answered",
"Answered", "Engaged", "Abandoned", "Engaged", "Abandoned", "Abandoned",
"Abandoned", "Abandoned", "Engaged", "Abandoned", "Abandoned",
"Abandoned", "Abandoned", "Answered", "Abandoned", "Abandoned",
"Abandoned", "Abandoned", "Abandoned", "Abandoned", "Engaged",
"Abandoned", "Abandoned", "Abandoned", "Abandoned", "Abandoned",
"Abandoned", "Engaged", "Abandoned", "Abandoned", "Abandoned",
"Abandoned", "Abandoned", "Answered", "Abandoned", "Engaged",
"Abandoned", "Answered")
df<-as.data.frame(cbind(UserId,DateTime,Status))
df$DateTime<-as.numeric(df$DateTime)
df$DateTime<-as.POSIXct(df$DateTime, origin = "1970-01-01 00:00:00")
View(df)
Это чтобы напоминать фрейм данных, с которым я в настоящее время работаю: ниже показан предполагаемый результат: -
#The intented result
UserId<-c("816194b2aa6ae09dea56876b68bb8244", "73ae725b039b4ca0d3727bb2497a717d",
"eb431db274a6b6d2b2c7e455f4e5780b", "104b0cfb910f7c9de318c05c3c305be2",
"e1bd4a520d490a4151882e0a136d3f28", "e1bd4a520d490a4151882e0a136d3f28",
"f4904b5d962d3e8be1dfcc237fbb7e70", "f4904b5d962d3e8be1dfcc237fbb7e70",
"54eca3518ca03ca0ae883ff3aaad79fe", "1320319e0b65f95b71ce5650b592039b")
OrigTime<-structure(c(1546300596, 1546300596, 1546300762, 1546300966, 1546338093,
1546366255, 1546301038, 1546315566, 1546300866, 1546299594),
class = c("POSIXct", "POSIXt"), tzone = "UTC")
LastTime<-structure(c(1546300596, 1546300596, 1546301468, 1546301009, 1546346046,
1546366284, 1546301098, 1546315566, 1546300866, 1546299594),
class = c("POSIXct", "POSIXt"), tzone = "UTC")
Calls<-c(1, 1, 22, 2, 10, 3, 3, 1, 1, 1)
Status<-c("Answered", "Answered", "Answered", "Answered", "Abandoned",
"Answered", "Abandoned", "Answerered", "Abandoned", "Answered")
Successful<-c("Y", "Y", "Y", "Y", "N", "Y", "N", "Y", "N", "Y")
callattempts<-as.data.frame(cbind(UserId,OrigTime,LastTime,Calls,Status,Successful))
callattempts$OrigTime<-as.numeric(callattempts$OrigTime)
callattempts$OrigTime<-as.POSIXct(callattempts$OrigTime, origin = "1970-01-01 00:00:00")
callattempts$LastTime<-as.numeric(callattempts$LastTime)
callattempts$LastTime<-as.POSIXct(callattempts$LastTime, origin = "1970-01-01 00:00:00")
head(callattempts,10)
UserId OrigTime LastTime Calls Status Successful
1 816194b2aa6ae09dea56876b68bb8244 2018-12-31 23:56:36 2018-12-31 23:56:36 1 Answered Y
2 73ae725b039b4ca0d3727bb2497a717d 2018-12-31 23:56:36 2018-12-31 23:56:36 1 Answered Y
3 eb431db274a6b6d2b2c7e455f4e5780b 2018-12-31 23:59:22 2019-01-01 00:11:08 22 Answered Y
4 104b0cfb910f7c9de318c05c3c305be2 2019-01-01 00:02:46 2019-01-01 00:03:29 2 Answered Y
5 e1bd4a520d490a4151882e0a136d3f28 2019-01-01 10:21:33 2019-01-01 12:34:06 10 Abandoned N
6 e1bd4a520d490a4151882e0a136d3f28 2019-01-01 18:10:55 2019-01-01 18:11:24 3 Answered Y
7 f4904b5d962d3e8be1dfcc237fbb7e70 2019-01-01 00:03:58 2019-01-01 00:04:58 3 Abandoned N
8 f4904b5d962d3e8be1dfcc237fbb7e70 2019-01-01 04:06:06 2019-01-01 04:06:06 1 Answerered Y
9 54eca3518ca03ca0ae883ff3aaad79fe 2019-01-01 00:01:06 2019-01-01 00:01:06 1 Abandoned N
10 1320319e0b65f95b71ce5650b592039b 2018-12-31 23:39:54 2018-12-31 23:39:54 1 Answered Y
Вы можете видеть, что некоторые UserId находятся в фрейме данных callattempts дважды. Например, UserId «e1bd4a520d490a4151882e0a136d3f28» сделал 10 последовательных вызовов в период с 10:21:33 1 января 2019 г. по 12:34:06 1 января 2019 г. через оператора (N). Эти 10 вызовов go рассматриваются как 1 единственная попытка дозвониться до оператора, поскольку UserId «e1bd4a520d490a4151882e0a136d3f28» не выполняет еще один вызов службы в течение 60 минут после его последнего вызова, который произошел в 2019-01-01 12:34:06 .
Однако UserId «e1bd4a520d490a4151882e0a136d3f28» делает еще одну попытку дозвониться до оператора почти через 6 часов, делает 3 звонка и на 3-й звонок переходит к оператору (Отвечено; Успешно = Y). Эти 3 последовательных вызова засчитываются как 1 попытка, потому что этот пользователь, наконец, получает ответ на 3-й вызов, следовательно, завершает это.
В случае UserId «816194b2aa6ae09dea56876b68bb8244» этот пользователь вызывает службу и переходит к оператору в их первый вызов (Отвечен; Успешно = Y), который засчитывается как 1 попытка дозвониться.
Напротив, UserId «54eca3518ca03ca0ae883ff3aaad79fe» вызывает службу один раз и немедленно кладет трубку (Отказано; Успешно = N); поскольку этот вызывающий абонент не пытается снова позвонить на горячую линию в течение 60 минут после последнего звонка, последний звонок преобразуется как 1 попытка.
Есть ли способ достичь того, что представлено в callattempts
кадре данных ? Будем очень признательны, если есть!