缩放 CASE WHEN 以检索非节假日日期

Posted

技术标签:

【中文标题】缩放 CASE WHEN 以检索非节假日日期【英文标题】:Scale CASE WHEN to retrieve non-holiday dates 【发布时间】:2019-03-26 15:16:58 【问题描述】:

我有一个包含开始日期和结束日期的记录的表格,所以我必须获取从星期五开始的每条记录,如果任何星期五是假期,则获取星期四,如果星期五和星期四是假期,则获取星期三等上...

目前我有两张表 TableA 用于记录,Calendar 用于休假。

我的TableA 看起来像这样:

id beg         end
--------------------------
1  11/01/2019  14/01/2019
2  10/01/2019  14/01/2019
3  09/01/2019  15/01/2019
...

日历如下所示:

iddate    date        weekday isholiday
---------------------------------------
20190109  09/01/2019  3       0 --0=False / 1=True
20190110  10/01/2019  4       0
20190111  11/01/2019  5       1
...

对于这两个表,我使用WHERE EXISTS 来获取星期五和实际显示结果的假日条件:

SELECT *
FROM TableA t
WHERE EXISTS (SELECT 1
              FROM dbo.Calendar AS c
              WHERE c.date = CAST(t.BEG AS DATETIME)
                AND c.weekday = CASE
                                    WHEN (C.weekday = 5 AND C.isholiday = 0)  
                                       THEN 5 --keep friday
                                    --WHEN ((C.weekday= 4 AND C.isholiday= 1) OR (C.weekday= 5 AND C.isholiday= 1)) THEN 3 --keep wednesday / not working
                                       ELSE 4 --keep thursday
                                    END
                AND DATEPART(yyyy, T.beg) = 2019)
ORDER BY 
    CAST(INI AS [datetime])

如果星期五是节假日,它将显示如下:

id beg         end
--------------------------
2  10/01/2019  14/01/2019
3  09/01/2019  15/01/2019

如果周五和周四是节假日,应该显示:

id beg         end
--------------------------
3  09/01/2019  15/01/2019

用这个WHEN ((C.weekday= 4 AND C.isholiday= 1) OR (C.weekday= 5 AND C.isholiday= 1)) 放大它只会破坏整个查询,我得到 - 几乎 - 随机日期。有什么方法可以在不过度扩展查询的情况下对其进行扩展?

【问题讨论】:

您的日历表是​​否完整,因为 2019 年有 365 行?此外,您的预期结果与您最初的描述不符 - 标有“如果星期五是假期”的部分包括星期三的活动,即使星期四不是假期您能否澄清一下?最后,您使用的是哪个版本的 SQL Server? @Brian 是的,它有 30 年的数据。我的意思是我需要每周最后一个工作日的每一行,所以如果星期五是日历表上的假期,最后一个工作日将是星期四,我使用的是 SQL Server 2008。谢谢! 【参考方案1】:

根据您的评论,我会使用公用表表达式:

;With cte_Last_Day_Of_Week
As
(
    Select 
        c.iddate
        , c.date
        , Row_Number() Over (Partition By DatePart(Week, c.date) Order By c.date Desc) As RN
    From dbo.Calendar As c
    Where c.isholiday = 0
)

Row_Number() 将用1 的值标记每周最后一个非节假日的日期。然后,您可以像加入表格一样加入它。

让我知道这是否有意义。

【讨论】:

以上是关于缩放 CASE WHEN 以检索非节假日日期的主要内容,如果未能解决你的问题,请参考以下文章

C++ Windows API - 如何检索字体缩放百分比

CASE WHEN 2 日期匹配的 SQL 查询

hql 查询以检索具有最大日期值的数据

MS Access Query 以检索订单日期列中最新日期的记录

以 html 形式从 MYSQL 中检索日期

CASE WHEN 中连续日期的平均小时数差异