Postgres:定义每个开发人员的最长条纹(以天为单位)

Sam*_*lli 3 sql postgresql

有一个软件项目包含一些数据,如下表所示.在此表中,我们有开发人员,他在系统中进行了一些更改(管理请求)的日期以及这些日期中每个日期之间的差异.

 SeqID  | developer |   MR date     |   dates diff
--------+-----------+---------------+----------------
1       |   Ivy     |   01/02/2012  |   0
2       |   Ivy     |   02/02/2012  |   1
3       |   Ivy     |   03/02/2012  |   1
4       |   Ivy     |   10/02/2012  |   7
5       |   Ivy     |   13/02/2012  |   3   
6       |   Ivy     |   14/02/2012  |   1
1       |   Ken     |   17/02/2012  |   0
2       |   Ken     |   20/02/2012  |   3
3       |   Ken     |   22/02/2012  |   2
4       |   Ken     |   23/02/2012  |   1
5       |   Ken     |   24/02/2012  |   1
6       |   Ken     |   25/02/2012  |   1
7       |   Ken     |   01/03/2012  |   4
8       |   Ken     |   05/03/2012  |   4
1       |   Bob     |   19/02/2012  |   0
2       |   Bob     |   23/02/2012  |   4
3       |   Bob     |   01/03/2012  |   6
4       |   Bob     |   02/03/2012  |   1
5       |   Bob     |   03/03/2012  |   1
6       |   Bob     |   05/03/2012  |   2
Run Code Online (Sandbox Code Playgroud)

我想知道的是最长条纹是什么(连续变化在最大1天的差异中完成).与我们在每个开发人员的github统计数据中非常相似的东西.所以结果表就像:

developer   |   longest streak  
------------+------------------------   
    Ivy     |   2   
    Ken     |   3   
    Bob     |   2   
Run Code Online (Sandbox Code Playgroud)

我尝试的解决方案是计算开发人员使用diff date = 1分组的行数.但这不会返回想要的结果.
根据结果​​表,计数应该像:Dev = Ivy; 最长连胜= 01/02/2012至03/02/2012 = 2天等等
.你们有些人可以帮我解决这个问题吗?谢谢,

Gor*_*off 8

这样做有一个技巧.如果从日期中减去不断增加的数字序列,那么对于连续的日期,它们将保持不变.然后我们可以使用它来为每个开发人员定义组.

select developer, max(numdays) as maxseq
from (select developer, grp, min(MRDate) as MR_start, max(MRDate) as MR_end,
             count(distinct MRDate) as numdays
      from (select t.*,
                  (MRDate - dense_rank() over (partition by developer order by date)) as grp
            from t
           ) t
      group by developer, grp
     ) t
group by developer;
Run Code Online (Sandbox Code Playgroud)

如果你知道有每个日期至多一个记录,那么你可以使用row_number(),而不是dense_rank()count(*)代替count(distinct MRDate).