我正在为学校做一个项目,并且在一周内为三个人提供了一个关于gps录音的数据库。我试图根据他们之间的时间将这些录音分组到旅行中。如果录音距离录音前300秒内,它们被视为同一行程的一部分,否则,它们被视为不同行程的一部分。
到目前为止,我已经设法计算了第n行的记录和第n-1行的记录之间的时差,我现在正在尝试创建一个合并记录介绍行程的功能。在另一种编程语言中,这本来就很容易,但在本课程中我们使用的是PostgreSQL,我并不精通它。
为了解决这个问题,我试图创建一个带有变量的函数,该函数在每次两次录制之间的时差大于300秒时增加,并根据变量分配每一行。这是我目前所获得的,虽然目前,该变量一直重置X,因此将所有行分配给trip 1 ......
CREATE OR REPLACE FUNCTION tripmerge(time_diff double precision)
RETURNs integer AS $$
declare
X integer := 1;
ID integer;
BEGIN
IF time_diff < 300 THEN
ID = X;
ELSE
ID =X;
X:=X+1;
END IF;
RETURN ID;
END;$$
LANGUAGE plpgsql;
如何更改X
不会一直重置?我正在使用PostgreSQL 9.1。
编辑:
这是我正在使用的表格:
curr_rec (timestamp), prev_rec (timestamp), time_diff (double precision)
这是数据集的一个示例:
'2013-11-14 05:22:33.991+01',null ,null
'2013-11-14 09:15:40.485+01','2013-11-14 05:22:33.991+01',13986.494
'2013-11-14 09:17:04.837+01','2013-11-14 09:15:40.485+01',84.352
'2013-11-14 09:17:43.055+01','2013-11-14 09:17:04.837+01',38.218
'2013-11-14 09:23:24.205+01','2013-11-14 09:17:43.055+01',341.15
预期结果会添加一列:
tripID
1
2
2
2
3
我认为这个小提琴应该有效:http://sqlfiddle.com/#!1/4e3e5/1/0
答案 0 :(得分:3)
此查询仅使用curr_rec
,而不使用其他冗余的预先计算列:
SELECT 1 + count(step OR NULL) OVER (ORDER BY curr_rec) AS trip_id
FROM (
SELECT curr_rec
,lag(curr_rec) OVER (ORDER BY curr_rec) AS prev_rec
,curr_rec - lag(curr_rec) OVER (ORDER BY curr_rec)
> interval '5 min' AS step
FROM timestamps
) x;
主要功能包括:
lag()
,用于查看前一行是否超过5分钟。 (只需使用interval
进行比较,无需提取秒数)count()
- 这只是带有OVER
子句的基本聚合函数。step OR NULL
仅离开TRUE
或NULL
,其中只有TRUE
计入正在运行的计数中,从而达到您想要的结果。SQL Fiddle(以你提供的那个为基础)。