我正在运行Postgres 9.6。我有一个用户表:
id | integer | | not null | nextval('user_id_seq'::regclass)
name | character varying | | not null |
我有一个history
表:
actioned_by | integer | | |
category | character varying | | not null |
t_actioned | timestamp without time zone | | not null |
我想要一种用整数字段num_days
注释每个用户的方法,该字段指示他们在24小时内有多少不同的动作。
我知道如何获取每个用户活跃的不同日历天的计数:
SELECT d.actioned_by, COUNT(*) AS cnt FROM
(SELECT date_trunc('day', t_actioned) AS day, actioned_by
FROM history
GROUP BY day, actioned_by) d
GROUP BY actioned_by
ORDER BY cnt DESC;
但是有没有一种方法可以测量从第一次采取行动之时起的时间段,以允许在五分钟内登录到午夜并在十分钟后离开的人?
出于分析目的,我偶尔会运行它,因此它的运行速度是否慢并不重要。
答案 0 :(得分:0)
SELECT
*,
trunc( -- E
extract(epoch FROM ( -- C
t_actioned - -- B
first_value(t_actioned) OVER (PARTITION BY actioned_by ORDER BY t_actioned) -- A
)) / 60 / 60 / 24 -- D
) + 1 as num_days -- F
FROM history
A:使用窗口函数first_value
https://www.postgresql.org/docs/current/static/tutorial-window.html
B:获取行的当前时间戳与用户的第一个时间戳之间的差异。结果是一个间隔
C:将间隔转换为秒
D:将秒转换为天
E:四舍五入到整天(减少数字)
F:添加1是因为您不希望天数的差异(一天中的2个时间戳产生的天数== 0)而是天数
测试数据:
actioned_by t_actioned
----------- -------------------
1 2018-09-08 23:55:00
1 2018-09-09 00:10:00
1 2018-09-10 00:05:00
1 2018-09-10 00:15:00
2 2018-09-09 20:15:00
2 2018-09-10 02:15:00
2 2018-09-10 08:15:00
2 2018-09-10 14:15:00
2 2018-09-10 20:14:00
结果:
actioned_by t_actioned num_days
----------- ------------------- --------
1 2018-09-08 23:55:00 1.0
1 2018-09-09 00:10:00 1.0
1 2018-09-10 00:05:00 2.0
1 2018-09-10 00:15:00 2.0
2 2018-09-09 20:15:00 1.0
2 2018-09-10 02:15:00 1.0
2 2018-09-10 08:15:00 1.0
2 2018-09-10 14:15:00 1.0
2 2018-09-10 20:14:00 1.0