如何在给定的持续时间内获得15分钟的块

时间:2018-03-27 15:44:50

标签: sql sql-server sql-server-2017

我希望在给定的时间内获得15分钟的大块时间。

例如。 @start_time = '10:00 am' @end_time = '1:00 pm'
然后它应该返回一个这样的表:  

10:00 AM 
10:15 AM
10:30 AM
10:45 AM
11:00 AM
11:15 AM
11:30 AM
11:45 AM
...and so on till
12:45 PM 

我在谷歌搜索了很多,但没有发现任何有用的东西。我怎么能这样做?

4 个答案:

答案 0 :(得分:0)

也许您可以开始使用递归CTE:

;WITH cte AS(
SELECT CAST('2018-01-01 10:00:00.000' AS DATETIME) AS StartDate
UNION ALL
SELECT DATEADD(MI, 15, StartDate)
FROM cte
WHERE StartDate < '2018-01-01 13:00:00.000'
)

SELECT *
FROM cte
OPTION (MAXRECURSION 32767) 

注意:OPTION (MAXRECURSION 32767)设置最大递归。省略此行,默认值为100。

答案 1 :(得分:0)

使用递归CTE:

DECLARE @StartTime TIME = '10:00'
DECLARE @EndTime TIME = '13:00'

;WITH Recu AS
(
    SELECT
        GeneratedTime = @StartTime

    UNION ALL

    SELECT
        GeneratedTime = DATEADD(MINUTE, 15, R.GeneratedTime)
    FROM
        Recu AS R
    WHERE
        R.GeneratedTime < @EndTime
)
SELECT
    *
FROM
    Recu AS R
OPTION
    (MAXRECURSION 32000)

/*
Result:
    GeneratedTime
    10:00:00.0000000
    10:15:00.0000000
    10:30:00.0000000
    10:45:00.0000000
    11:00:00.0000000
    11:15:00.0000000
    11:30:00.0000000
    11:45:00.0000000
    12:00:00.0000000
    12:15:00.0000000
    12:30:00.0000000
    12:45:00.0000000
    13:00:00.0000000
*/

答案 2 :(得分:0)

使用Tally表:

DECLARE @Start_Time time = '10:00:00', @End_time time = '13:00:00';

SELECT DATEADD(MINUTE, Number, @Start_Time)
FROM Tally
WHERE Number % 15 = 0
AND DATEADD(MINUTE, Number, '1900-01-01' + CAST(@Start_Time As DateTime)) < 
                            '1900-01-01' + CAST(@End_time As DateTime)

如果您还没有Tally表,可以使用此脚本创建它:

SELECT TOP 10000 IDENTITY(int,0,1) AS Number -- Note: Starts at 0!
    INTO Tally
    FROM sys.objects s1       
    CROSS JOIN sys.objects s2 
ALTER TABLE Tally ADD CONSTRAINT PK_Tally PRIMARY KEY CLUSTERED (Number)

如果您不知道计数表是什么,以及为什么要有计数表,请阅读Jeff Moden的The "Numbers" or "Tally" Table: What it is and how it replaces a loop

答案 3 :(得分:0)

使用系统表制作行,并使用DATEADD计算期间:

declare @start_time time = '10:00:00 AM', @end_time time = '01:00:00 PM';

select convert(time, dateadd(MINUTE, (n-1)*15, convert(datetime, @start_time))) x, *
from (select top (DATEDIFF(hh, @start_time, @end_time)*4) ROW_NUMBER() over (order by o1.object_id) n from sys.all_objects o1) num

非常快