根据SQL Server中的日期和规则识别记录子集

时间:2016-06-16 11:05:47

标签: sql-server tsql select sql-server-2012

我有一个如下所示的数据集:

enter image description here

我需要识别 Linked 设置为1的行,但只有在按照图片中 ToDate 降序排序时它们在一起的行。

换句话说,我希望能够识别这些记录(已编辑):

enter image description here

这是一个简化的数据集,实际上会有更多的记录......

定义记录是否被链接的逻辑是记录的 FromDate 是否在前一个日期的 ToDate 的8周内...但这是testData所以可能不完美

最好的方法是什么?

3 个答案:

答案 0 :(得分:2)

您可以使用LAG()LEAD()分析函数:

SELECT * FROM (
    SELECT t.*,
           LAG(t.linked,1,0) OVER(ORDER BY t.FromDate DESC) as rnk_1, --Next one
           LEAD(t.linked,1,0) OVER(ORDER BY t.FromDate DESC) as rnk_2, -- Last one,
           LEAD(t.linked,2,0) OVER(ORDER BY t.FromDate DESC) as rnk_3 -- Last two,
    FROM YourTable t) s
WHERE ((s.rnk_1 = 1 OR s.rnk_2 = 1) AND s.linked = 1) OR 
      (s.rnk_2 = 1 and s.rnk_3 = 1 and s.linked = 0)
ORDER BY s.FromDate DESC

这将导致记录具有linked = 1且上一个/下一个记录也为1.

答案 1 :(得分:1)

使用LAGLEAD函数,您可以在给定排序条件的情况下检查上一行/下一行值。

您可以使用以下DDL获得所需的数据集:

;
WITH    CTE_LagLead
          AS (
              SELECT    FromDate,
                        ToDate,
                        NoOfDays,
                        Weeks,
                        Linked,
                        LAG(Linked, 1, 0) OVER (ORDER BY ToDate DESC) LinkedLag,
                        LEAD(Linked, 1, 0) OVER (ORDER BY ToDate DESC) LinkedLead
              FROM      @table
             )
    SELECT  FromDate,
            ToDate,
            NoOfDays,
            Weeks,
            Linked
    FROM    CTE_LagLead
    WHERE   Linked = 1 AND
            (LinkedLag = 1 OR
             LinkedLead = 1)
    ORDER BY ToDate DESC;

See working example

答案 2 :(得分:0)

这是我想出的答案:

Select 
    * 
from 
    #tmpAbsences 
where 
    idcol between 1 AND (
    Select TOP 1 idcol from #tmpAbsences where Linked=0)

这包括下图中的第7行:

enter image description here