我正在使用SQL,我需要获得此结果,但我不知道如何。我需要的是获取时间间隔。请参考下面的示例
----------------------
| Time | Interval|
----------------------|
| 9:03 | 9:00 |
| 9:02 | 8:30 |
| 9:32 | 9:00 |
| 9:33 | 9:30 |
-----------------------
样本间隔矩阵
-----------------------------
| Interval | Time |
-----------------------------|
| 9:00 | 9:02 - 9:31:59 |
| 9:30 | 9:32 - 10:01:59|
| 10:00 | 10:02- 10:31:59|
----------------------- ------
所以基本上9:03 - 9:32
以9:00
的时间间隔存在,而9:33 - 10:02
以9:30的间隔存在
我有这个查询
SELECT CONVERT(time(7),DATEADD(MINUTE,(DATEPART(MINUTE, '10:32:00') /
30)*30,(DATEADD(HOUR, DATEDIFF(HOUR, 0, '10:32:00'), 0))))
但这是我能想到的最远的结果,结果应该是10:00
间隔。您可以为我指明正确的方向,或者给我一些提示
答案 0 :(得分:1)
我认为这将为您提供所需的东西:
declare @testtable table (thedate time )
insert into @testtable values ( '09:03'), ('09:02'), ('09:32'), ('09:33')
select
thedate,
case when datepart(minute,thedate) between 0 and 2 then dateadd(minute, -30,cast(cast(datepart(hour,thedate) as varchar)+':00' as time))
when datepart(minute,thedate) between 3 and 32 then cast(cast(datepart(hour,thedate) as varchar)+':00' as time)
else dateadd(minute, +30,cast(cast(datepart(hour,thedate) as varchar)+':00' as time))
end
from @testtable
产生:
09:03:00.0000000 09:00:00.0000000
09:02:00.0000000 08:30:00.0000000
09:32:00.0000000 09:00:00.0000000
09:33:00.0000000 09:30:00.0000000
答案 1 :(得分:1)
以下解决方案将DATEDIFF
与MINUTE
相对于00:02
的偏移量使用以纠正差异,然后通过将分钟作为 integers来操作,从而将时间间隔缩短为30分钟并执行/ 30 * 30
,最后将结果转换回TIME
。
DECLARE @Times TABLE (ClockTime TIME)
INSERT INTO @Times (ClockTime)
VALUES
('08:57'),
('08:58'),
('08:59'),
('09:00'),
('09:01'),
('09:02'),
('09:03'),
('09:05'),
('09:31'),
('09:31:59'),
('09:32'),
('10:32'),
('23:02'),
('23:03'),
('23:31:15')
SELECT
T.ClockTime,
MinutesMinus2 = DATEDIFF(MINUTE, '00:02', T.ClockTime),
MinutesMinus2On30Intervals = DATEDIFF(MINUTE, '00:02', T.ClockTime) / 30 * 30,
MinutesMinus2On30IntervalsAsTime = CONVERT(
TIME,
DATEADD(
MINUTE,
DATEDIFF(MINUTE, '00:02', T.ClockTime) / 30 * 30, -- MinutesMinus2On30Intervals
0))
FROM
@Times AS T
结果:
+------------------+---------------+----------------------------+----------------------------------+
| ClockTime | MinutesMinus2 | MinutesMinus2On30Intervals | MinutesMinus2On30IntervalsAsTime |
+------------------+---------------+----------------------------+----------------------------------+
| 08:57:00.0000000 | 535 | 510 | 08:30:00.0000000 |
| 08:58:00.0000000 | 536 | 510 | 08:30:00.0000000 |
| 08:59:00.0000000 | 537 | 510 | 08:30:00.0000000 |
| 09:00:00.0000000 | 538 | 510 | 08:30:00.0000000 |
| 09:01:00.0000000 | 539 | 510 | 08:30:00.0000000 |
| 09:02:00.0000000 | 540 | 540 | 09:00:00.0000000 |
| 09:03:00.0000000 | 541 | 540 | 09:00:00.0000000 |
| 09:05:00.0000000 | 543 | 540 | 09:00:00.0000000 |
| 09:31:00.0000000 | 569 | 540 | 09:00:00.0000000 |
| 09:31:59.0000000 | 569 | 540 | 09:00:00.0000000 |
| 09:32:00.0000000 | 570 | 570 | 09:30:00.0000000 |
| 10:32:00.0000000 | 630 | 630 | 10:30:00.0000000 |
| 23:02:00.0000000 | 1380 | 1380 | 23:00:00.0000000 |
| 23:03:00.0000000 | 1381 | 1380 | 23:00:00.0000000 |
| 23:31:15.0000000 | 1409 | 1380 | 23:00:00.0000000 |
+------------------+---------------+----------------------------+----------------------------------+
如果您的时间偏差发生变化,您还可以使用TIME
变量来设置偏移量:
DECLARE @TimeOffset TIME = '00:02'
SELECT
Interval = CONVERT(
TIME,
DATEADD(
MINUTE,
DATEDIFF(MINUTE, @TimeOffset, T.ClockTime) / 30 * 30,
0))
FROM
@Times AS T
答案 2 :(得分:0)
请注意,我已将interval
时间范围字符串更改为开始时间和结束时间。如果数据为字符串形式,请考虑转换为2种单独的时间数据类型。否则,您将需要在查询中执行一些字符串解析
数据格式正确后,查询就是INNER JOIN
declare @sample table
(
[Time] time(0)
)
insert into @sample
values ('09:03'),
('09:02'),
('09:32'),
('09:33')
declare @interval table
(
[Interval] time(0),
[Time_Start] time(0),
[Time_End] time(0)
)
insert into @interval
values ('09:00', '09:02', '09:31:59'),
('09:30', '09:32', '10:01:59'),
('10:00', '10:02', '10:31:59')
select s.Time, i.Interval
from @sample s
inner join @interval i on s.Time between i.Time_Start and i.Time_End
答案 3 :(得分:0)
我将这个想法的答案提供给其他人,但我认为这更简洁易懂
DECLARE @date time = '07-04-2019 10:32:00'
SELECT CONVERT(time(7),DATEADD(MINUTE,(DATEPART(MINUTE,
CASE WHEN DATEPART(MINUTE, @date) = 31 THEN DATEADD(minute,-2,@date) WHEN DATEPART(MINUTE, @date) = 1 THEN DATEADD(minute,-2,@date) ELSE @date END
) / 30)*30,(DATEADD(HOUR, DATEDIFF(HOUR, 0, CASE WHEN DATEPART(MINUTE,@date) = 1 THEN DATEADD(HOUR,-1,@date) ELSE @date END), 0))))