SELECT grid.t5
,min(t."time") AS min_time
-- ,array_agg(extract(min FROM t."time")) AS 'players_on' -- optional
,avg(t.players) AS avg_players
,avg(t.servers) AS avg_servers
FROM (
SELECT generate_series(min("time")
,max("time"), interval '5 min') AS t5
FROM tbl
) grid
LEFT JOIN tbl t ON t."time" >= grid.t5
AND t."time" < grid.t5 + interval '5 min'
GROUP BY grid.t5
ORDER BY grid.t5;
Wyjaśnij
-
Podzapytanie
grid
tworzy jeden wiersz na każde 5 minut od minimum do maksimum „time"
w twoim stole. -
LEFT JOIN z powrotem do tabeli dzielenia danych w 5-minutowych odstępach. Ostrożnie uwzględnij dolna ramka i wyklucz górna granica.
-
Aby upuścić 5-minutowe przedziały, w których nic się nie stało, użyj
JOIN
w miejsceLEFT JOIN
. -
Aby czasy siatki zaczynały się o godzinie 0:00, 5:00 itd., zaokrąglij w dół
min("time")
wgenerate_series()
.
Więcej wyjaśnień w tych powiązanych odpowiedziach:
Grupuj według interwały danych
PostgreSQL:liczenie wierszy dla zapytania 'w minutach'
Poza tym:nie użyłbym time
jako identyfikator. To zastrzeżone słowo w standardowym SQL
oraz nazwę funkcji/typu w Postgresie.