You need to enable JavaScript to run this app.
最新活动
大模型
产品
解决方案
定价
生态与合作
支持与服务
开发者
了解我们

基于tbl_Shift表计算指定日期工作日:SQL查询结果异常求助

解决指定时间段工作日计算错误的问题

咱们先拆解下你的问题:现有查询返回26天,但实际2018年5月31天、每周2个休息日(周六+周日),正确工作日应该是23天。问题出在你的查询逻辑没有准确统计出时间段内所有的休息日数量,咱们一步步修正:

原查询的核心问题

你的现有代码用总天数减去周数(默认每周扣1天),再加1次第二个休息日的扣除,这完全没考虑到5月实际有多少个周六和周日——2018年5月有4个周六、4个周日,总共8个休息日,31-8=23才是正确结果。

正确的解决方案

我们需要先生成指定日期范围内的每一天,再逐一判断该日期是否属于tbl_Shift定义的休息日,最后统计非休息日的数量。这里用CTE递归生成日期序列:

DECLARE @StartDate DATETIME 
DECLARE @EndDate DATETIME 
SET @StartDate = '2018/05/01' 
SET @EndDate = '2018/05/31'

WITH DateRange AS (
    -- 初始化起始日期
    SELECT @StartDate AS DateVal
    UNION ALL
    -- 递归生成后续所有日期
    SELECT DATEADD(dd, 1, DateVal)
    FROM DateRange
    WHERE DateVal < @EndDate
)
SELECT COUNT(*) AS TotalWorkDays
FROM DateRange d
-- 关联休息日配置表
CROSS JOIN HRM.tbl_Shift s
WHERE 
    -- 判断当前日期的星期名称不在休息日列表中
    DATENAME(WEEKDAY, d.DateVal) NOT IN (
        s.OffDay1,
        -- 仅当启用第二个休息日时,才将其纳入判断
        CASE WHEN s.IsAlternateOffDay2 = 1 THEN s.OffDay2 ELSE NULL END
    )
-- 递归默认上限100层,开启最大递归支持整月日期生成
OPTION (MAXRECURSION 0);

额外注意点

  • 如果你的数据库语言是中文,DATENAME(WEEKDAY, ...)会返回“星期日”这类中文名称,需要确保tbl_Shift里的OffDay1/OffDay2存储的名称和它一致;或者改用DATEPART(WEEKDAY, ...)匹配数字(比如周日=1、周六=7,注意数据库SET DATEFIRST的设置)。
  • 这个方法的优势是灵活适配任何休息日规则,哪怕后续调整休息日配置,查询逻辑不需要大改。

内容的提问来源于stack exchange,提问作者Doonie Darkoo

火山引擎 最新活动