2013-08-21 58 views
2

我有這樣的SQL Server表:十大事件持續時間

TimeStamp (datetime)| Alarm (string) | Active (bool) 
01.08.2013 1:30:05 | Alarm 1    | false 
01.08.2013 1:29:54 | Alarm 2    | true 
01.08.2013 1:28:43 | Alarm 1    | true 
01.08.2013 1:27:21 | Alarm 3    | false 
01.08.2013 1:26:35 | Alarm 1    | false 
01.08.2013 1:25:34 | Alarm 1    | true 

我已經顯示前10個報警事件:

SELECT TOP 10 Alarm, COUNT(Alarm) AS Occurrence 
FROM MyTable 
WHERE (Active = 'True') 
GROUP BY Alarm 
ORDER BY Occurrence DESC 

我現在需要前10個報警時間

目標是讓每個警報的持續時間總和(從真到假)。

我真的被封鎖在這,我想我需要迭代每行,併爲每個滿足的報警求和時間值。

但我不知道如何用SQL查詢來做到這一點。任何幫助或方向將不勝感激。

預先感謝


@Roman PEKAR:SQL服務器2008

@戈登·利諾夫:預期輸出=>頂部10報警持續時間(當警報爲真))

time[min] | Alarm 

50 | Alarm 2 
34 | Alarm 3 
22 | Alarm 1 

... 
+0

你有什麼版本的SQL Server? –

+2

請提供樣本輸出。目前還不清楚您希望結果是針對問題中的數據。 –

+0

如何計算報警2和報警3的時間,因爲每個報警只發生一次(報警2 = 1真,報警3 = 1假)?另外,對於報警1,你需要2行還是隻有1.我的意思是,你要計算總持續時間或兩個持續時間,1:25:34到1:26:35,然後是1:28:43到1 :30:05? –

回答

1

你可以用cross apply找到之後的on

select top 10 active.Alarm 
,  active.TimeStamp as TimeOn 
,  active.TimeStamp as TimeOff 
,  datediff(second, active.TimeStamp, inactive.TimeStamp) as Duration 
from YourTable active 
cross apply 
     (
     select top 1 * 
     from YourTable inactive 
     where inactive.Active = 'false' 
       and inactive.Alarm = active.Alarm 
       and inactive.TimeStamp > active.TimeStamp 
     order by 
       inactive.TimeStamp 
     ) inactive 
where active.Active = 'true' 
order by 
     Duration desc 

See it working at SQL Fiddle.

+0

非常感謝您的回答,它可以幫助我很多! – Thierry

1

下面是另一種解決方案,其可以是更有效的。

;with a as 
(
    select a.Alarm 
    , a.Active 
    , a.[Timestamp] 
    , Sequence = dense_rank() over 
       (
        partition by a.Alarm, a.Active 
        order by a.[TimeStamp] 
       ) 
    from #YourTable a 
), 
b as 
(
    select a.Alarm 
    , Start = b.[Timestamp] 
    , Stop = a.[Timestamp] 
    from a 
    left outer join a b 
    on b.Alarm = a.Alarm 
    and b.Sequence = a.Sequence 
    and b.Active = 'true' 
    where a.Active = 'false' 
) 
select b.Alarm 
, DurationMinutes = sum(datediff(millisecond, b.Start, b.Stop)/1000.0/60.0) 
from b 
group by b.Alarm 
+0

可能更高效,但也要求更高的數據一致性。如果第一行是先前警報的結束(「關閉」條目),則查詢將返回負值持續時間。 – Andomar

+0

@Andomar真的。您可以將'and b.Timestamp