使用SQL计算用户输入日期范围内的并发日期

时间:2016-12-21 15:56:06

标签: sql sql-server

用户将输入日期范围,并且我希望在 SQL 中输出所述设备的并发使用次数之间的所有日期,包括该范围。

在此示例中,用户日期范围为03/08/2016 to 03/09/2016,因此您可以在下面看到我在这些日期之间或之间包含任何内容(按类别分组,但我只是使用&#39简化了此处; powerchair&#39)

表模式如下;

trans_date | trans_end_date | eq_category
17/03/2016 | 16/10/2016     | POWERCHAIR
08/08/2016 | 08/08/2016     | POWERCHAIR
12/08/2016 | 12/08/2016     | POWERCHAIR
17/08/2016 | 18/08/2016     | POWERCHAIR
22/08/2016 | 22/08/2016     | POWERCHAIR
26/08/2016 | 26/08/2016     | POWERCHAIR
02/09/2016 | 02/09/2016     | POWERCHAIR

我想输出;

date       | concurrent_use
03-08-2016 |    1
04-08-2016 |    1
05-08-2016 |    1
06-08-2016 |    1
07-08-2016 |    1
08-08-2016 |    2
09-08-2016 |    1
10-08-2016 |    1
11-08-2016 |    1
12-08-2016 |    2
13-08-2016 |    1
14-08-2016 |    1
15-08-2016 |    1
16-08-2016 |    1
17-08-2016 |    2
18-08-2016 |    2
19-08-2016 |    1
20-08-2016 |    1
21-08-2016 |    1
22-08-2016 |    2
23-08-2016 |    1
24-08-2016 |    1
25-08-2016 |    1
26-08-2016 |    2
27-08-2016 |    1
28-08-2016 |    1
29-08-2016 |    1
30-08-2016 |    1
31-08-2016 |    1
01-09-2016 |    1
02-09-2016 |    2
03-09-2016 |    1

任何事情1 or 0,我都可以过滤掉,因为当天没有任何设备同时出现。

我不认为这是一个差距/岛屿问题,但我试图在 SQL 语句中尝试这个问题。

2 个答案:

答案 0 :(得分:1)

您需要一组数字或日期。所以,如果你想要那个范围内的所有东西:

with d as (
      select cast('2016-08-03' as date) as d
      union all
      select dateadd(day, 1, d.d)
      from d
      where d < '2016-09-03'
     )
select d.d, count(s.trans_date)
from d left join
     schema s
     on d.d between s.trans_date and s.trans_date_end
group by d.d;

我不确定开始日期和结束日期是否都包含在范围内。

答案 1 :(得分:1)

尝试如下。您需要使用递归cte生成日期。然后我们需要计算范围内每个日期的出现次数。

     ;WITH CTE
     AS (SELECT CONVERT(DATE, '2016-08-03', 103) DATE1
         UNION ALL
         SELECT Dateadd(DAY, 1, DATE1) AS DATE1
         FROM   CTE
         WHERE  Dateadd(DD, 1, DATE1) <= '2016-09-03')
SELECT C.DATE1,
       Count(1) OCCURENCES
FROM   CTE C
       JOIN #TABLE1 T
         ON C.DATE1 BETWEEN [TRANS_DATE] AN [TRANS_END_DATE]
GROUP  BY C.DATE1