SQL Server中如何精准获取前一天00:00:00至23:59:59的数据?
我来帮你搞定这个问题~你的核心需求是不管任务在当天几点运行,都要精准获取前一天全天(00:00:00 到 23:59:59)的数据,原SQL的问题出在没处理时间部分,导致范围误包含了当天的部分数据。
先分析原语句的问题
你写的:
select * from table where CreatedDateTime BETWEEN DATEADD(day, -1, GETDATE()) AND DATEADD(day, -0, GETDATE())
当任务在2018-05-22 01:00:00运行时,DATEADD(day, -1, GETDATE())会返回2018-05-21 01:00:00,而DATEADD(day, -0, GETDATE())就是当前时间2018-05-22 01:00:00——这个区间是从昨天凌晨1点到今天凌晨1点,自然会包含今天0点到1点的数据,这就是结果不符合预期的原因。
两种正确的实现方式
方式一:更严谨的区间判断(推荐)
这种写法能避免毫秒级精度的坑,不会漏掉或多统计数据:
SELECT * FROM table WHERE CreatedDateTime >= CAST(DATEADD(day, -1, GETDATE()) AS DATE) AND CreatedDateTime < CAST(GETDATE() AS DATE)
- 解释:
CAST(GETDATE() AS DATE)会剥离当前时间的时分秒,得到当天的起始日期(比如2018-05-22 00:00:00); DATEADD(day, -1, CAST(GETDATE() AS DATE))就是前一天的起始日期2018-05-21 00:00:00;- 条件
CreatedDateTime < CAST(GETDATE() AS DATE)意味着所有小于当天0点的数据,也就是前一天23:59:59.999及之前的所有记录,完美覆盖前一天全天。
方式二:明确指定前一天的结束时间
如果你习惯用BETWEEN,可以针对SQL Server的datetime精度调整写法:
SELECT * FROM table WHERE CreatedDateTime BETWEEN CAST(DATEADD(day, -1, GETDATE()) AS DATE) AND DATEADD(millisecond, -3, CAST(GETDATE() AS DATE))
- 解释:SQL Server的
datetime类型精度是3.33毫秒,DATEADD(millisecond, -3, CAST(GETDATE() AS DATE))会把当天0点往前推3毫秒,得到前一天的23:59:59.997,这是不会进位到第二天的最大时间值,确保覆盖前一天所有数据。
不管任务在当天几点运行,这两种写法都能精准锁定前一天的完整数据集。
内容的提问来源于stack exchange,提问作者KatePillay
相关产品推荐
相关产品推荐

