sql—获取日期组中的第一行,其中有一个不间断的日期序列

t1qtbnec  于 2021-07-26  发布在  Java
关注(0)|答案(2)|浏览(242)
DECLARE @TestData TABLE (
    Idntty    Int    Not Null
    ,[DATE] DATE NOT NULL
    ,[TYPE] VARCHAR(20) NOT NULL
    )
INSERT INTO @TestData VALUES 
(1,  '2016-03-01', 'Inventory'),
(2,  '2016-04-01', 'Inventory'), 
(3,  '2016-06-01', 'Inventory'),  
(4,  '2016-07-01', 'Inventory'), 
(5,  '2016-08-01', 'Inventory'),  
(6,  '2016-09-01', 'Inventory'),
(7,  '2017-01-01', 'Inventory'), 
(8,  '2017-02-01', 'Inventory'),  
(9,  '2017-03-01', 'Inventory'),
;

基本上,我需要得到最后一组中的第一行,其中有一个没有中断的日期序列。
例如,此处的“2016-03-01”不正确,因为缺少“2016-05-01”,因此此日期记录的顺序存在中断。
分组的标准是连续日期,因此在示例中有3个分组,因为有2个中断,一个是因为缺少“2016-06-01”,第二个是因为缺少“2016-10-01”、“2016-11-01”、“2016-12-01”:

(1,  '2016-03-01', 'Inventory'),
(2,  '2016-04-01', 'Inventory'),

and

(3,  '2016-06-01', 'Inventory'),  
(4,  '2016-07-01', 'Inventory'), 
(5,  '2016-08-01', 'Inventory'),  
(6,  '2016-09-01', 'Inventory'), 

and

(7,  '2017-01-01', 'Inventory'), 
(8,  '2017-02-01', 'Inventory'),  
(9,  '2017-03-01', 'Inventory'),

所以我需要'2017-01-01'作为连续序列的第一个日期记录和最后一个序列的输出。
我尝试使用标准的缺口和孤岛解决方案,但没有取得任何成功,比如在这里应用什么。
我只想用sql来解决这个问题。我使用的是sql server 2008。

2q5ifsrm

2q5ifsrm1#

这确实是一个缺口和岛屿问题。基本上你想从最后一个岛开始。下面是一个使用窗口函数的选项:

select max(date) res
from (
    select t.*, lag(date) over(partition by type order by Idntty) lag_date
    from mytable t
) t
where lag_date is null or date > dateadd(day, 1, lag_date)

在子查询中, lag() 提供“上一条”记录的日期。然后,外部查询筛选日期与上一条记录(即每个岛的开始日期)相差大于1天的行,并获取此结果集中的最大日期。

ttcibm8c

ttcibm8c2#

一种方法是使用循环。请尝试以下操作:

DECLARE CUR CURSOR FAST_FORWARD FOR SELECT DISTINCT [DATE] FROM @TestData ORDER BY [DATE]
DECLARE @DATE DATE
DECLARE @PREV_DATE DATE = NULL, @FINAL_GRP_DATE DATE, @CN INT = -1
OPEN CUR
FETCH NEXT FROM CUR INTO @DATE
WHILE (@@FETCH_STATUS = 0)
BEGIN
    IF DATEDIFF(MM, @PREV_DATE, @DATE) = 1
    BEGIN
        SET @FINAL_GRP_DATE = @DATE 
        SET @CN = -1
    END
    ELSE
    BEGIN
        SET @CN = 0
    END
    SET @PREV_DATE = @DATE
    FETCH NEXT FROM CUR INTO @DATE
END
CLOSE CUR
DEALLOCATE CUR

SELECT @FINAL_GRP_DATE

请在这里找到小提琴。

相关问题