当时间范围在两天之间时如何获取特定时间范围内的记录

问题描述

我正在尝试查询特定的时间范围:

  • 即1/1/2021 - 1/31/2021

  • 上述日期的所有天的上午 5:55 - 次日凌晨 5:00 之间

解决方法

您需要从时间戳中提取时间部分(T-SQL 的 datetime 类型)并除日期过滤器外还通过它们进行过滤。

dbfiddle here

declare
  @dt_from datetime,@dt_to datetime,@tm_from time,@tm_to time,@dt datetime
;
  
select
  @dt = convert(datetime,'2021-02-10 11:48:36',120),@dt_from = convert(date,'2021-02-01',23),@dt_to = convert(date,'2021-02-28',@tm_from = convert(time,'05:55:00',@tm_to = convert(time,'05:00:00',120)
;

with a as (
  select @dt as dt union all
  select dateadd(hour,20,@dt) union all
  select dateadd(hour,-15,-6,@dt) union all
  select dateadd(day,-30,@dt) union all
  select convert(datetime,'2021-02-01 00:01:02',120) union all
  select convert(datetime,'2021-02-28 20:01:02',120)
)
select *
from dt
/*Restrict dates*/
where dt >= @dt_from
  and dt < dateadd(day,1,@dt_to)
  and (
    /*Exclude time intervals between 05:00 and 05:55*/
    cast(dt as time) <= @tm_to
    or cast(dt as time) >= @tm_from
  )

或者,如果您只需要整个时间范围都在您的日期范围内的情况(例如,排除开始日期从 00:00 到 05:00 和结束日期从 05:55 到 23:59:59 的时间):

select *
from dt
where dt between @dt_from and @dt_to
  and (
    /*Exclude time intervals between 05:00 and 05:55*/
    cast(dt as time) <= @tm_to
    or cast(dt as time) >= @tm_from
  )
  /*Exclude time intervals at boundary dates*/
  and not(
    (cast(dt as date) = @dt_from and cast(dt as time) <= @tm_to)
    or (cast(dt as date) = @dt_to and cast(dt as time) >= @tm_from)
  )