从SQL表

时间:2016-04-20 09:21:56

标签: sql sql-server sql-server-2008 sql-server-2008-r2

我正在处理应用程序的假期表,我必须根据该表中的假期列表找到下一个工作日。

如果输入是工作日,我们希望返回空白/ NULL,但如果是假期,我们希望返回下一个工作日。

我的假期表包含以下示例数据。 第一个日期列用于startdate,第二个用于enddate。而不是连续两个假期使用startdate和enddate。客户创建了两个单独的行。

现在我必须编写一个select查询,它将根据该示例数据提供下一个工作日。

假设我通过'2016-04-20 00:00:00.000'作为条件日期,那么查询应该返回'2016-04-22 00:00:00.000'作为工作日期并且连续两个假日。

2016    2016-04-20 00:00:00.000 2016-04-20 00:00:00.000 Test
2016    2016-04-21 00:00:00.000 2016-04-21 00:00:00.000 Test2
2016    2016-04-28 00:00:00.000 2016-04-28 00:00:00.000 Test3

3 个答案:

答案 0 :(得分:0)

你可以试试这个:

--create table holidays(y int, ds datetime, de datetime, hname varchar(10));
--insert into holidays  values
--(2016,'2016-04-20 00:00:00.000','2016-04-20 00:00:00.000','Test'),
--(2016,'2016-04-21 00:00:00.000','2016-04-21 00:00:00.000','Test2'),
--(2016,'2016-04-28 00:00:00.000','2016-04-28 00:00:00.000','Test3'),
--(2016,'2016-04-22 00:00:00.000','2016-04-22 00:00:00.000','Test4')
CREATE FUNCTION dbo.getNextDate(@dateToCheck datetime) RETURNS Datetime
AS
BEGIN

 RETURN(
select top 1 dateadd(d,1,de)  from 

(select y,
  MIN(ds) as ds, 
  MAX(ds) as de
from 
 (
  Select 
   *, 
   ROW_NUMBER() OVER(ORDER BY ds asc) as ranking 
   from holidays
 ) t  
 group by y,(CAST(ds AS INT)-Ranking)
)t
where @dateToCheck BETWEEN ds AND de
)
END

经过测试:

SELECT dbo.getNextDate('2016-04-23 00:00:00.000')-- returns NULL
SELECT dbo.getNextDate('2016-04-21 00:00:00.000')-- returns 2016-04-23 00:00:00.000

SQL demo link

答案 1 :(得分:0)

如果下面提到的代码有效,请告诉我。此代码首先制作一个日历表,然后从日期中排除星期六和星期日。

declare @mn date = (select min(yourdate) from table)
select top 1 a.caldate
from
(
select dateadd(dd,row_number() over (order by (select 1)) - 1,@mn) as caldate
from sys.all_objects
) as a
where a.caldate not in (select cast(yourdate as date) as yourdate from TableA) and datename(dw,a.caldate) not in ('Saturday','Sunday') and a.caldate >= '2016-04-20'

答案 2 :(得分:0)

使用此结构设置假期表:

CREATE TABLE holidays (
    [year] int,
    [ds] datetime,
    [de] datetime,
    [description] nvarchar(50)
)

您可以创建一个迭代日期的函数,直到找到正确的日期

CREATE FUNCTION dbo.getNextDate(@dateToCheck datetime) RETURNS Datetime
AS
BEGIN
    DECLARE @tempDate datetime
    SET @tempDate=DATEADD(day,1,@dateToCheck)
    WHILE EXISTS(SELECT * FROM holidays WHERE @tempDate BETWEEN ds AND de)
    BEGIN
        SET @tempDate=DATEADD(day,1,@tempDate)
    END

    RETURN @tempDate
END

这是一个非常基本的第一个近似,但它应该有用。