查询以查找超过特定间隔的所有时间戳

时间:2014-09-02 00:07:01

标签: sql postgresql aggregate-functions window-functions

我正在使用postgres对用户活动进行一些分析。我有一个表格,列出了每个用户发出的所有请求(网页浏览量)以及请求的时间戳,我正在尝试查找每个用户的不同会话数。为了简单起见,我将每一组请求与其他请求分开一小时或更长时间作为一个独特的会话。数据看起来像这样:

id|          request_time|         user_id
1    2014-01-12 08:57:16.725533    1233
2    2014-01-12 08:57:20.944193    1234
3    2014-01-12 09:15:59.713456    1233
4    2014-01-12 10:58:59.713456    1234

如何编写查询以获取每个用户的会话数?

1 个答案:

答案 0 :(得分:3)

在每个差距> = 1小时后开始新会话:

SELECT user_id, count(*) AS distinct_sessions
FROM (
   SELECT user_id
        ,(lag(request_time, 1, '-infinity') OVER (PARTITION BY user_id
                                                  ORDER BY request_time)
           <= request_time - '1h'::interval) AS step -- start new session
   FROM   tbl
   ) sub
WHERE  step
GROUP  BY user_id
ORDER  BY user_id;

假设request_time NOT NULL

说明:

  • 在子查询sub中,检查新会话开始时的每一行。使用lag()的第三个参数提供默认-infinity,它低于任何时间戳,因此始终为第一行启动新会话。

  • 在外部查询中计算新会话开始的次数。消除step = FALSE并按用户计算。

替代解释

如果你真的想计算至少有一个请求发生的时间(我不认为你这样做,但另一个答案假定的那样),你会:

SELECT user_id
     , count(DISTINCT date_trunc('hour', request_time)) AS hours_with_req
FROM   tbl
GROUP  BY 1
ORDER  BY 1;