月度报表SQL日期格式问题:无法获取月末记录的解决办法
解决Oracle月度报表日期范围漏抓月末记录的问题
问题根源
你当前的SQL里,last_day(add_months(trunc(sysdate,'mm'),-1))返回的是上月最后一天的00:00:00,但如果BEG_DT_TM字段包含时分秒(比如2023-05-31 14:30:00),这个时间会晚于last_day返回的日期,自然不会被between匹配到,导致月末带时间的记录被漏掉。
解决方案
推荐用以下两种方法解决:
方法1:截断BEG_DT_TM到日期维度
如果不担心索引失效问题,可以直接把BEG_DT_TM截断到日期部分再做匹配:
trunc(BEG_DT_TM) between add_months(trunc(sysdate,'mm'),-1) and last_day(add_months(trunc(sysdate,'mm'),-1))
注意:如果BEG_DT_TM字段建了索引,trunc(BEG_DT_TM)会让索引失效,查询性能可能下降。
方法2:用“小于下月第一天”代替“等于月末”(推荐)
这是更优的方案,既不会漏数据,又能保留索引可用性:
BEG_DT_TM >= add_months(trunc(sysdate,'mm'),-1) and BEG_DT_TM < trunc(sysdate,'mm')
逻辑很简单:trunc(sysdate,'mm')是当月第一天的00:00:00,上月所有的时间(包括月末最后一秒2023-05-31 23:59:59)都小于这个值,完美覆盖你要的上月全时段数据。
可选方法3:手动设置月末最后一秒
如果一定要用between,可以把上限设为月末最后一秒:
BEG_DT_TM between add_months(trunc(sysdate,'mm'),-1) and last_day(add_months(trunc(sysdate,'mm'),-1)) + 1 - interval '1' second
但这种写法不如方法2简洁,也容易因为时间精度(比如毫秒级)出现遗漏。
内容的提问来源于stack exchange,提问作者Bag
相关产品推荐
相关产品推荐

