SQL 按日期范围分区

Posted

技术标签:

【中文标题】SQL 按日期范围分区【英文标题】:SQL partition by on date range 【发布时间】:2018-07-30 12:28:16 【问题描述】:

假设这是我的桌子:

ID  NUMBER  DATE
------------------------
1   45      2018-01-01
2   45      2018-01-02
2   45      2018-01-27

我需要使用 partition by 和 row_number 来分隔一个日期与另一个日期之间的差异大于 5 天。上例的结果是这样的:

ROWNUMBER   ID  NUMBER  DATE
-----------------------------
1           1   45      2018-01-01
2           2   45      2018-01-02
1           3   45      2018-01-27

我的实际查询是这样的:

SELECT ROW_NUMBER() OVER(PARTITION BY NUMBER ODER BY ID DESC) AS ROWNUMBER, ...

但是您可以注意到,它不适用于日期。我怎样才能做到这一点?

【问题讨论】:

制作一个包含开始日期范围和结束日期范围的日期表,然后给每个范围一个 id。按日期加入日期表,按日期范围的id分区 【参考方案1】:

你可以使用lag函数:

select *, row_number() over (partition by number, grp order by id) as [ROWNUMBER]
from (select *, (case when datediff(day, lag(date,1,date) over (partition by number order by id), date) <= 1 
                      then 1 else 2 
                 end) as grp
      from table
     ) t;

【讨论】:

【参考方案2】:

通过使用lagdatediff 函数

select * from
    (
    select t.*,
           datediff(day,
                    lag(DATE) over (partition by NUMBER order by id),
                    DATE
                   ) as diff
    from  t 
      ) as TT where  diff>5

http://sqlfiddle.com/#!18/130ae/11

【讨论】:

【参考方案3】:

我认为您想使用lag()datediff() 以及累积和来识别然后使用row_number()

select t.*,
       row_number() over (partition by number, grp order by date) as rownumber
from (select t.*,
             sum(grp_start) over (partition by number order by date) as grp
      from (select t.*,
                   (case when lag(date) over (partition by number order by date) < dateadd(day, 5, date)
                            then 1 else 0
                    end) as grp_start
            from t
           ) t
     ) t;

【讨论】:

以上是关于SQL 按日期范围分区的主要内容,如果未能解决你的问题,请参考以下文章

按日期范围分区 PostgreSQL 扫描所有分区

在 SQL Server 2012 中创建以日期为范围分区的表

sql 在表格中分割新的日期范围分区

MySQL 分区,因为用户和时间戳日期范围

SQL - 按日期范围查询

如何在 Hive SQL 中按日期范围独家加入?