Шкала CASE WHEN для получения нерабочих дат - PullRequest
0 голосов
/ 26 марта 2019

У меня есть таблица, содержащая записи с датами начала и окончания, поэтому мне нужно захватить каждую запись, начавшуюся в пятницу, и, если любая пятница является выходным, получить четверг, а если пятница и четверг - выходные, получить среду и т. Д.на ...

В настоящее время у меня есть две таблицы 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)) просто разбивает весь запрос, и яполучить почти все случайные датыЕсть ли какой-нибудь способ увеличить его без чрезмерного расширения запроса?

1 Ответ

1 голос
/ 26 марта 2019

На основании вашего комментария я бы использовал общее табличное выражение:

;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,Затем вы можете присоединиться к этому, как к столу.

Дайте мне знать, если это имеет смысл.

...