Calculate Actual Downtime ignoring overlap in dates/times

前端 未结 2 1832
-上瘾入骨i
-上瘾入骨i 2021-01-14 16:10

I\'m trying to work out how to calculate actual downtime for various applications from data I\'m storing within a table.

At the moment I\'m just calculating the dif

2条回答
  •  南笙
    南笙 (楼主)
    2021-01-14 16:30

    I had a similar problem, and I got it answered in my question How to Consolidate Blocks of Time?

    In your case, this is accomplished with a top 1 self outer apply to get the overlap, and then use either the Overlap's Start time, or if null, the normal Record's end time as the end time.

    CREATE TABLE Downtime (
        Application VARCHAR(25), 
        DowntimeStart DATETIME,
        DowntimeEnd DATETIME,
        Expected INT
    )
    
    INSERT Downtime (Application, DowntimeStart, DowntimeEnd, Expected) VALUES -- Act/Exp
        ('Application Demo', '2014-11-20 17:31:01.467', '2014-11-20 18:01:01.243', 30) -- 30/30
        ,('Application Demo', '2014-11-28 17:59:00.987', '2014-11-28 18:09:02.167', 26) -- 10/26
        ,('Application Demo', '2014-11-28 18:00:01.403', '2014-11-28 18:25:01.443', 0) -- 25/0
        ,('Application Demo', '2014-11-29 19:13:08.580', '2014-11-30 05:30:01.763', 617) -- 617/617
        ,('Application Demo', '2014-11-30 01:55:01.953', '2014-11-30 03:54:01.730', 0)
    
    
    SELECT
        Records.Application, Records.DowntimeStart, Records.DowntimeEnd, Records.Expected
      , DATEDIFF(minute, Records.DowntimeStart, COALESCE(Overlap.DowntimeStart, Records.DowntimeEnd)) AS Actual
    --  , Overlap.Application, Overlap.DowntimeStart, Overlap.DowntimeEnd -- For Verification Purposes
    FROM Downtime Records
      OUTER APPLY (
        SELECT TOP 1 Overlap.Application, Overlap.DowntimeStart, Overlap.DowntimeEnd
        FROM Downtime Overlap
        WHERE Records.Application = Overlap.Application
          AND Overlap.DowntimeStart > Records.DowntimeStart
          AND Overlap.DowntimeStart BETWEEN Records.DowntimeStart AND Records.DowntimeEnd
        ORDER BY Overlap.DowntimeStart
        ) Overlap
    

    Here's the SQLFiddle with the solution.

提交回复
热议问题