在有序行集中计算相等的连续值

Rom*_*siv 5 sql postgresql window-functions gaps-and-islands postgresql-9.6

我有一个包含两列的表:

CREATE TABLE actions (
  action_time TIMESTAMP NOT NULL DEFAULT CURRENT_TIMESTAMP,
  "action" text NOT NULL
);
Run Code Online (Sandbox Code Playgroud)

以及其中的以下数据:

        action_time         | action 
----------------------------+--------
 2016-12-30 14:12:33.353269 | a
 2016-12-30 14:12:38.536818 | b
 2016-12-30 14:12:43.305001 | a
 2016-12-30 14:12:49.432981 | a
 2016-12-30 14:12:53.536397 | b
 2016-12-30 14:12:57.449101 | b
 2016-12-30 14:13:01.592785 | a
 2016-12-30 14:13:06.192907 | b
 2016-12-30 14:13:11.249181 | b
 2016-12-30 14:13:13.690897 | b
(10 rows)
Run Code Online (Sandbox Code Playgroud)

您可以假定在action_time列中没有重复的值。

如何计算从上一个动作开始连续执行的相同动作的数量?

连续执行的操作数量没有限制,任何操作都可以是最后一个。而且,对各种不同的动作没有限制:我仅使用两个来简化示例数据。

对于此示例数据,我希望结果为3。这是因为最后一个动作是“ b”,并且连续发生了3次。

我认为可以结合使用窗口函数和WITH RECURSIVE子句来实现该解决方案,但是我不知道该怎么做。

Eel*_*lke 1

这应该可以做到。

SELECT COUNT(*)
FROM actions
WHERE action_time > (
SELECT action_time
  FROM actions 
  WHERE action <> (SELECT action FROM actions ORDER BY action_time DESC LIMIT 1) 
ORDER BY action_time DESC LIMIT 1);
Run Code Online (Sandbox Code Playgroud)

最里面的查询

SELECT action FROM actions ORDER BY action_time DESC LIMIT 1
Run Code Online (Sandbox Code Playgroud)

决定最后的动作。

查询

SELECT action_time
  FROM actions 
  WHERE action <> (SELECT action FROM actions ORDER BY action_time DESC LIMIT 1) 
ORDER BY action_time DESC LIMIT 1
Run Code Online (Sandbox Code Playgroud)

找到具有不同操作的最后一行。

最外面的查询查找该行之后的所有行。