在我构建一个可以在x个工作日后计算日期的函数的过程中,我遇到了这个函数:
ALTER FUNCTION [dbo].[AddBusinessDays] (@Date date,@n INT)
RETURNS DATE AS BEGIN
DECLARE @d INT;
SET @d=4-SIGN(@n)*(4-DATEPART(DW,@Date));
RETURN DATEADD(D,@n+((ABS(@n)+@d-2)/5)*2*SIGN(@n)-@d/7,@Date) END
此功能有效但我需要将其与我的假期表链接,以便它可以省略我所在国家/地区的特定假期。当我在今天的日期(26-04-2017)运行它时,我在24-05-2017之后的20个工作日内得到这个日期,所以它只省略了周末。如何修改它以便它也会跳过假期? 如果我发出一个问题请求太多,请道歉。我是SQL的初学者。谢谢
答案 0 :(得分:0)
不是依赖于难以理解的计算,而是明确地确定工作日期并从中进行选择会更容易吗?例如:
DECLARE @NthWorkingDay INT = 33;
DECLARE @holidays TABLE
(
holiday DATE ,
[description] VARCHAR(500)
);
INSERT @holidays
( holiday, description )
VALUES ( '20170519', '...' ),
( '20170501', '...' ),
( '20170611', '...' ),
( '20170704', '...' );
DECLARE @sunday INT ,
@saturday INT;
-- 1/1/2000 is a known date - Saturday
SET @saturday = DATEPART(WEEKDAY, DATEFROMPARTS(2000, 1, 1));
SET @sunday = DATEPART(WEEKDAY, DATEFROMPARTS(2000, 1, 2));
WITH tally
AS ( SELECT TOP 5000
ROW_NUMBER() OVER ( ORDER BY t1.object_id ) AS N
FROM master.sys.all_columns t1
CROSS JOIN master.sys.all_columns t2
),
dates ( theDate )
AS ( SELECT DATEADD(DAY, N - 1, CAST(GETDATE() AS DATE))
FROM tally
),
workDates ( workingDay, workingDate )
AS ( SELECT ROW_NUMBER() OVER ( ORDER BY theDate ) ,
theDate
FROM dates
WHERE DATEPART(WEEKDAY, theDate) NOT IN ( @saturday, @sunday )
AND theDate NOT IN ( SELECT holiday
FROM @holidays )
)
SELECT workingDate
FROM workDates
WHERE workingDay = @NthWorkingDay;