SQL Server计算当前日期的天数,不包括另一个表中的天数

时间:2018-06-18 15:35:11

标签: sql-server date

我正在尝试编写一个允许我采用下表的查询:

| Username | Startdate | Points |
|----------|-----------|--------|
| XXY      | 15-03-18  |      0 |
| YYX      | 12-02-18  |      1 |
| ZZY      | 10-06-18  |      2 |

并计算当天的天数,不包括表2中用户缺席的天数。

| Username | Startdate | Enddate  |
|----------|-----------|----------|
| XXY      | 20-03-18  | 25-03-18 |

另外一个问题,我需要两个表在当前日期之前每天都有一行。我该怎么做?

更新:我在表1 DATEDIFF(DAY,Startdate,GETDATE())中尝试了这个,这给了我天数。但我需要从中减去5天(见表2)

3 个答案:

答案 0 :(得分:0)

One method would be to do the below:

USE Sandbox;
GO

CREATE TABLE Dates (SkipDate date);
GO

INSERT INTO Dates
VALUES ('20180605'),('20180617');
GO

WITH VTE AS (
    SELECT CONVERT(date,S) StartDate, CONVERT(date, E) EndDate
    FROM (VALUES('20180601','20180606'),
                ('20180601','20180618')) V(S,E))
SELECT StartDate,
       EndDate,
       DATEDIFF(DAY, StartDate, EndDate) AS DaysBetween,
       DATEDIFF(DAY, StartDate, EndDate) - SkipDates AS DaysMinusSkipped
FROM VTE
     CROSS APPLY (SELECT COUNT(*) AS SkipDates
                  FROM Dates
                  WHERE SkipDate >= StartDate
                    AND SkipDate <= EndDate) AS SD;
GO

If you wanted to create something that means you don't need to write that SQL everytime instead, you can create a table-value function:

CREATE FUNCTION dbo.DateDiffSkip (@StartDate date, @EndDate date)
RETURNS TABLE
AS RETURN

    SELECT DATEDIFF(DAY, @StartDate, @EndDate) - COUNT(SkipDate) AS DateDiffSkip
    FROM Dates D
    WHERE D.SkipDate >= @StartDate
      AND D.SkipDate <=  @EndDate;

GO

Then, your SQL would be:

WITH VTE AS (
    SELECT CONVERT(date,S) StartDate, CONVERT(date, E) EndDate
    FROM (VALUES('20180601','20180606'),
                ('20180601','20180618')) V(S,E))
SELECT StartDate,
       EndDate,
       DATEDIFF(DAY, StartDate, EndDate) AS DaysBetween,
       DDS.DateDiffSkip AS DaysMinusSkipped
FROM VTE
     CROSS APPLY dbo.DateDiffSkip(StartDate, EndDate) DDS;
GO
--Clean up
DROP FUNCTION DateDiffSkip;
DROP TABLE Dates;

答案 1 :(得分:0)

select 
datediff(day, table1.StartDate, getdate()) - datediff(day, table2.StartDate, table2.Enddate)
from table1 
join table2 on table1.Username = table2.Username

答案 2 :(得分:0)

这可以使用多个DATEDIFF函数计算。这也计算每个用户多次缺席:

declare @t table ([UserName] char(3), [StartDate] Date, [Points] int)
insert into @t values ('XXY', '2018-03-15', 0), ('YYX', '2018-02-12', 1), ('ZZY', '2018-06-10', 2)

declare @a table ([UserName] char(3), [StartDate] Date, [EndDate] Date)
insert into @a values ('XXY', '2018-03-20', '2018-03-25')

select t.*, datediff(d, t.[StartDate], cast(getdate() as date)) - isnull(sum(datediff(d, a.[StartDate], a.[EndDate])), 0) as [DaysNotAbsent]
from @t t
left join @a a on t.UserName = a.UserName
group by t.UserName, t.StartDate, t.Points