ниже для BigQuery Standard SQL
их нужно разрезать на более мелкие куски, если разрыв между сообщениями превышает 1 час:
#standardSQL
WITH `project.dataset.table` AS (
SELECT 2 conversation, TIMESTAMP '2018-06-22 00:01:46.456 UTC' dt UNION ALL # group 1
SELECT 2, '2018-06-22 00:07:12.178 UTC' UNION ALL # group 1
SELECT 2, '2018-06-22 00:16:46.456 UTC' UNION ALL # group 1
SELECT 2, '2018-06-22 01:07:42.178 UTC' UNION ALL # group 1
SELECT 2, '2018-06-22 12:51:28.540 UTC' UNION ALL # group 2
SELECT 2, '2018-06-22 13:00:40.486 UTC' UNION ALL # group 2
SELECT 2, '2018-06-22 19:54:30.031 UTC' # group 3
), conversation_groups AS (
SELECT
conversation, dt,
SUM(flag) OVER(PARTITION BY conversation ORDER BY dt) conversation_group
FROM (
SELECT
conversation, dt,
SIGN(IFNULL(TIMESTAMP_DIFF(dt, LAG(dt) OVER(PARTITION BY conversation ORDER BY dt), HOUR), 0)) flag
FROM `project.dataset.table`
)
)
SELECT *
FROM conversation_groups
ORDER BY conversation, dt
с результатом как
Row conversation dt conversation_group
1 2 2018-06-22 00:01:46.456 UTC 0
2 2 2018-06-22 00:07:12.178 UTC 0
3 2 2018-06-22 00:16:46.456 UTC 0
4 2 2018-06-22 01:07:42.178 UTC 0
5 2 2018-06-22 12:51:28.540 UTC 1
6 2 2018-06-22 13:00:40.486 UTC 1
7 2 2018-06-22 19:54:30.031 UTC 2
Мне нужно получить среднее время, проведенное в разговоре
#standardSQL
WITH `project.dataset.table` AS (
SELECT 2 conversation, TIMESTAMP '2018-06-22 00:01:46.456 UTC' dt UNION ALL # group 1
SELECT 2, '2018-06-22 00:07:12.178 UTC' UNION ALL # group 1
SELECT 2, '2018-06-22 00:16:46.456 UTC' UNION ALL # group 1
SELECT 2, '2018-06-22 01:07:42.178 UTC' UNION ALL # group 1
SELECT 2, '2018-06-22 12:51:28.540 UTC' UNION ALL # group 2
SELECT 2, '2018-06-22 13:00:40.486 UTC' UNION ALL # group 2
SELECT 2, '2018-06-22 19:54:30.031 UTC' # group 3
), conversation_groups AS (
SELECT
conversation, dt,
SUM(flag) OVER(PARTITION BY conversation ORDER BY dt) conversation_group
FROM (
SELECT
conversation, dt,
SIGN(IFNULL(TIMESTAMP_DIFF(dt, LAG(dt) OVER(PARTITION BY conversation ORDER BY dt), HOUR), 0)) flag
FROM `project.dataset.table`
)
)
SELECT conversation, AVG(IF(duration = 0, NULL, duration)) avg_duration
FROM (
SELECT
conversation, conversation_group,
TIMESTAMP_DIFF(MAX(dt), MIN(dt), MINUTE) duration
FROM conversation_groups
GROUP BY conversation, conversation_group
)
GROUP BY conversation
ORDER BY conversation
с результатом как
Row conversation avg_duration
1 2 37.0
Примечание: вы можете настроить логику вычисления avg на основе ваших конкретных потребностей / видения того, как это сделать, - но, как это делается выше, - сначала рассчитывается продолжительность каждой группы, а затем усредняется продолжительность в этих группах. принято - и обратите внимание: если продолжительность равна нулю, она заменяется на NULL, поэтому это не влияет на вычисление среднего значения. Длительность рассчитывается в МИНУТАХ, но вы можете использовать ВТОРЫЕ или все, что вам нужно