eine bestimmte Startzeit gegeben, können Sie Stunde Blöcke erhalten, indem die Anzahl der Minuten seit der Startzeit zu finden, und dividiert durch 60, dann diese Anzahl von Stunden zurück zu der Startzeit hinzufügen, z
DECLARE @StartTime DATETIME2(0) = '20160606 09:30';
WITH DummyData (mydatetime) AS
( SELECT TOP 200 DATEADD(MINUTE, ROW_NUMBER() OVER(ORDER BY [object_id]) - 1, @StartTime)
FROM sys.all_objects
)
SELECT HoursSinceStart = FLOOR(DATEDIFF(MINUTE, @StartTime, mydatetime)/60.0),
Display = DATEADD(HOUR, FLOOR(DATEDIFF(MINUTE, @StartTime, mydatetime)/60.0), @StartTime),
Records = COUNT(*)
FROM DummyData
WHERE myDateTime >= @StartTime
GROUP BY FLOOR(DATEDIFF(MINUTE, @StartTime, mydatetime)/60.0)
ORDER BY Display;
Welche gibt:
HoursSinceStart Display Records
0 2016-06-06 09:30:00 60
1 2016-06-06 10:30:00 40
2 2016-06-06 11:30:00 60
3 2016-06-06 12:30:00 20
ich die HoursSinceStart
Spalte, hoffentlich verlassen haben, in dekonstruiert die Logik in der Display
mit dieser Methode
Das Problem Spalte enthalten sind, zu unterstützen, ist, dass es geben Sie nur Ergebnisse für Blöcke, die vorhanden sind, wenn Sie auch diejenigen benötigen, die nicht alle Zeitblöcke mit einer Zahlentabelle generieren müssen, dann linken Sie zu Ihren Daten:
Sie können eine Reihe von Zahlen mit diesem schnell erzeugen:
DECLARE @StartTime DATETIME2(0) = '20160606 09:30';
-- GENERATE 10 ROWS
WITH N1 AS (SELECT N FROM (VALUES (1),(1),(1),(1),(1),(1),(1),(1),(1),(1)) n (N)),
-- CROSS JOIN THE 10 ROWS TO GET 100 ROWS
N2 (N) AS (SELECT 1 FROM N1 AS N1 CROSS JOIN N1 AS N2),
--CROSS JOIN THE 100 ROWS TO GET 10,000 ROWS
N3 (N) AS (SELECT 1 FROM N2 AS N1 CROSS JOIN N2 AS N2),
--APPLY ROW_NUMBER TO GET A SET OF NUMBERS FROM 0 - 99,999
Numbers (N) AS (SELECT ROW_NUMBER() OVER(ORDER BY N) - 1 FROM N3)
SELECT *,
TimeStart = DATEADD(HOUR, N, @StartTime),
TimeEnd = DATEADD(HOUR, N + 1, @StartTime)
FROM Numbers;
die so etwas wie gibt:
N TimeStart TimeEnd
--------------------------------------------------
0 2016-06-06 09:30:00 2016-06-06 10:30:00
1 2016-06-06 10:30:00 2016-06-06 11:30:00
2 2016-06-06 11:30:00 2016-06-06 12:30:00
3 2016-06-06 12:30:00 2016-06-06 13:30:00
4 2016-06-06 13:30:00 2016-06-06 14:30:00
5 2016-06-06 14:30:00 2016-06-06 15:30:00
6 2016-06-06 15:30:00 2016-06-06 16:30:00
7 2016-06-06 16:30:00 2016-06-06 17:30:00
Dann Sie Ihre Daten auf diese verbinden links können (Sie werden wahrscheinlich auch eine Endzeit brauchen);
DECLARE @StartTime DATETIME2(0) = '20160606 09:30',
@EndTime DATETIME2(0) = '20160606 15:30';
WITH DummyData (mydatetime) AS
( SELECT TOP 200 DATEADD(MINUTE, ROW_NUMBER() OVER(ORDER BY [object_id]) - 1, @StartTime)
FROM sys.all_objects
),
-- GENERATE NUMBERS
N1 AS (SELECT N FROM (VALUES (1),(1),(1),(1),(1),(1),(1),(1),(1),(1)) n (N)),
N2 (N) AS (SELECT 1 FROM N1 AS N1 CROSS JOIN N1 AS N2),
N3 (N) AS (SELECT 1 FROM N2 AS N1 CROSS JOIN N2 AS N2),
Numbers (N) AS (SELECT ROW_NUMBER() OVER(ORDER BY N) - 1 FROM N3),
TimePeriods AS
( SELECT TimeStart = DATEADD(HOUR, N, @StartTime),
TimeEnd = DATEADD(HOUR, N + 1, @StartTime)
FROM Numbers
WHERE DATEADD(HOUR, N, @StartTime) < @EndTime
)
SELECT tp.TimeStart, tp.TimeEnd, Records = COUNT(dd.myDateTime)
FROM TimePeriods AS tp
LEFT JOIN DummyData AS dd
ON dd.mydatetime >= tp.TimeStart
AND dd.mydatetime < tp.TimeEnd
GROUP BY tp.TimeStart, tp.TimeEnd
ORDER BY tp.TimeStart;
Welche 0 zurück, wo es keine Datensätze:
TimeStart TimeEnd Records
---------------------------------------------------------
2016-06-06 09:30:00 2016-06-06 10:30:00 60
2016-06-06 10:30:00 2016-06-06 11:30:00 60
2016-06-06 11:30:00 2016-06-06 12:30:00 60
2016-06-06 12:30:00 2016-06-06 13:30:00 20
2016-06-06 13:30:00 2016-06-06 14:30:00 0
2016-06-06 14:30:00 2016-06-06 15:30:00 0
Vielen Dank für Ihre Antwort. Ich brauchte einige Zeit, um zu verstehen, wie ich es mit meinen Daten verwenden kann, aber es funktioniert jetzt gut. :) – Aleph0