SQL滚动期为20天

时间:2013-06-18 14:48:42

标签: sql tsql date rolling-computation

我想知道找到最好的方法是什么,如果连续20天,事件的数量超过10个。

我正在尝试编写一个异常报告,但除了使用循环之外无法找出逻辑。

我已经包含了表的架构。

ID       |StartDate       |EndDate       |Area


---------+---------+---------+---------

12       |01-02-2013       |05-02-2013       |A12

14       |06-02-2013       |12-02-2013       |A13

15       |11-02-2013       |19-02-2013       |A14

19       |16-02-2013       |26-02-2013       |A15

21       |21-02-2013       |05-03-2013       |A16

24       |01-02-2013       |05-02-2013       |A17

26       |06-02-2013       |12-02-2013       |A18

28       |11-02-2013       |19-02-2013       |A19

30       |16-02-2013       |26-02-2013       |A20

33       |21-02-2013       |05-03-2013       |A21

我有一个部分解决方案: “

'DECLARE @START AS DATE
DECLARE @END AS DATE
SET @START= '20130201'
SET @END= '20130204'
SELECT     n.EVENT_DATE,
                          (SELECT     SUM(SESSIONS) AS Total_Sessionsn 
                            FROM          dbo.[Session]
                            WHERE      (EVENT_DATE BETWEEN DATEADD(d,-20,n.EVENT_DATE)     AND n.EVENT_DATE)
                            GROUP BY AREA_CODE, SITE_CODE) AS Sessions         
FROM         [dbo].[Session] AS n
WHERE     EVENT_DATE BETWEEN @START
 AND DATEADD(d,20+dbo.HolidayCount(@END,DATEADD(d,20,@END)) ,@END )'

得到了它。对于有兴趣在20个工作日内找到日期的人,我在下面添加了解决方案。 :)(我觉得很蠢!)

/****** Script for SelectTopNRows command from SSMS  ******/
SELECT TOP 1  [SK_CAL]
      ,[CAL_DATE]
      ,[CAL_CODE]
      ,[CAL_VALUE]
      ,[CAL_OPEN]
      ,[CAL_CLOSE]
FROM 
(SELECT TOP 20 [SK_CAL]
      ,[CAL_DATE]
      ,[CAL_CODE]
      ,[CAL_VALUE]
      ,[CAL_OPEN]
      ,[CAL_CLOSE]
  FROM [tempdb].[dbo].[tbCalendar]
  WHERE (CAL_DATE>'20130201' AND CAL_VALUE=1)
  ORDER BY SK_CAL ASC) n
  ORDER BY SK_CAL DESC

1 个答案:

答案 0 :(得分:0)

看看这是不是你想要的。我从CTE开始,它获得最早的StartDate和最新的EndDate来定义范围。然后另一个CTE推断出之间的所有日期。然后,对于该范围内的每个日期,我会看到在该日期之前的20天内有多少事件处于活动状态。我确定通过检查事件开始或结束日期是否在滚动的20天期间内发生,或者事件的开始和结束日期是否包含整个滚动的20天期限。

;with StartEnd as (
select 
    min(StartDate) StartRange, 
    max(EndDate) EndRange
 from 
    @Events
),
DatesInRange AS 
(
    SELECT StartRange AS RangeDate, dateadd(d,-19,StartRange) Rolling20Start from StartEnd
    UNION ALL
    SELECT DATEADD(DAY, 1, RangeDate), DATEADD(DAY, -18, RangeDate)
    FROM DatesInRange, StartEnd
    WHERE RangeDate < EndRange
)
select
    RangeDate,
    count(*)
from 
    DatesInRange
    left join @Events e on 
        e.StartDate between Rolling20Start and RangeDate or 
        e.EndDate between Rolling20Start and RangeDate or
        (e.StartDate < Rolling20Start and e.EndDate > RangeDate)
group by
    RangeDate
OPTION (MAXRECURSION 0)