以小时为单位追溯 Trino 中的事件数

时间:2021-04-30 16:59:54

标签: sql presto trino

我想追溯具有相同属性且时间戳与行时间戳最多相差一小时的行数。

举个例子,给定表格:

<头>
时间戳 ID
2021-04-17 01:51:44 A
2021-04-17 01:58:43 A
2021-04-17 02:01:32 B
2021-04-17 02:15:44 A
2021-04-17 02:57:44 A
2021-04-17 02:59:44 B
2021-04-17 03:15:44 B
2021-04-17 03:27:44 A
2021-04-17 03:31:44 A
2021-04-17 03:45:44 B
2021-04-17 03:52:44 B
2021-04-17 04:01:44 B
2021-04-17 04:23:44 A

我希望查询返回如下内容:

<头>
时间戳 ID 前一小时ID的出现次数
2021-04-17 01:51:44 A 1
2021-04-17 01:58:43 A 2
2021-04-17 02:01:32 B 1
2021-04-17 02:15:44 A 3
2021-04-17 02:57:44 A 3
2021-04-17 02:59:44 B 2
2021-04-17 03:15:44 B 2
2021-04-17 03:27:44 A 2
2021-04-17 03:31:44 A 3
2021-04-17 03:45:44 B 3
2021-04-17 03:52:44 B 4
2021-04-17 04:01:44 B 4
2021-04-17 04:23:44 A 3

我想单独加入表,或者使用分区作为替代方案,但没有达到我想要的目的。

提前致谢

1 个答案:

答案 0 :(得分:1)

您可以使用窗口函数:

COUNT(*) OVER (
    PARTITION BY id
    ORDER BY ts
    RANGE BETWEEN INTERVAL '1' HOUR PRECEDING AND CURRENT ROW)

从概念上讲,它的作用是:

  • 对于每一行,查看具有相同 id 的所有行
  • ts(升序)对行进行排序
  • 将窗口限制为 ts 在行的 ts 之前 1 小时和行的 ts 之间的所有行
  • 计算该帧中的行数。

这是一个完整的例子:

WITH t(ts, id) AS (
  VALUES
    (TIMESTAMP '2021-04-17 01:51:44', 'A'),
    (TIMESTAMP '2021-04-17 01:58:43', 'A'),
    (TIMESTAMP '2021-04-17 02:01:32', 'B'),
    (TIMESTAMP '2021-04-17 02:15:44', 'A'),
    (TIMESTAMP '2021-04-17 02:57:44', 'A'),
    (TIMESTAMP '2021-04-17 02:59:44', 'B'),
    (TIMESTAMP '2021-04-17 03:15:44', 'B'),
    (TIMESTAMP '2021-04-17 03:27:44', 'A'),
    (TIMESTAMP '2021-04-17 03:31:44', 'A'),
    (TIMESTAMP '2021-04-17 03:45:44', 'B'),
    (TIMESTAMP '2021-04-17 03:52:44', 'B'),
    (TIMESTAMP '2021-04-17 04:01:44', 'B'),
    (TIMESTAMP '2021-04-17 04:23:44', 'A')
)
SELECT ts,
       id,
       COUNT(*) OVER (
            PARTITION BY id
            ORDER BY ts
            RANGE BETWEEN INTERVAL '1' HOUR PRECEDING AND CURRENT ROW)
FROM t
ORDER BY ts

有关 RANGE 窗口框架如何工作的说明,请参阅 this blog post