sql >> Databasteknik >  >> RDS >> PostgreSQL

Summan av tidsskillnaden mellan raderna

Den speciella svårigheten är att inte missa tidsintervallen till den yttre tidsramen.
Förutsatt att nästa rad för ett givet id har alltid motsatt status.
Med kolumnnamnet ts istället för recordTime :

WITH span AS (
   SELECT '2014-03-01 13:00'::timestamp AS s_from  -- start of time range
        , '2014-03-01 14:00'::timestamp AS s_to    -- end of time range
   )
, cte AS (
   SELECT id, ts, status, s_to
        , lead(ts, 1, s_from) OVER w AS span_start
        , first_value(ts)     OVER w AS last_ts
   FROM   span s
   JOIN   tbl  t ON t.ts BETWEEN s.s_from AND s.s_to
   WINDOW w AS (PARTITION BY id ORDER BY ts DESC)
   )
SELECT id, sum(time_disconnected)::text AS total_disconnected
FROM  (
   SELECT id, ts - span_start AS time_disconnected
   FROM   cte
   WHERE  status = 'Connected'

   UNION  ALL  
   SELECT id, s_to - ts
   FROM   cte
   WHERE  status = 'Disconnected'
   AND    ts = last_ts
   ) sub
GROUP  BY 1
ORDER  BY 1;

Returnerar intervall som begärts.
ID:n utan poster inom det valda tidsintervallet visas inte. Du skulle behöva fråga dem ytterligare.

SQL-fiol.
Obs! Jag castar den resulterande total_disconnected till text i fiolen, eftersom typen interval visas i ett fruktansvärt format.

Lägg till ID:n utan inmatning inom den valda tidsramen


Lägg till i frågan ovan (före den sista ORDER BY 1 ):

...
UNION  ALL
SELECT id, total_disconnected
   FROM  (
   SELECT DISTINCT ON (id)
          t.id, t.status, (s.s_to - s.s_from)::text AS total_disconnected
   FROM   span     s
   JOIN   tbl      t ON t.ts < s.s_from  -- only from before time range
   LEFT   JOIN cte c USING (id)
   WHERE  c.id IS NULL         -- not represented in selected time frame
   ORDER  BY t.id, t.ts DESC   -- only the latest entry
   ) sub
WHERE  status = 'Disconnected' -- only if disconnected
ORDER  BY 1;

SQL-fiol.

Nu är det bara ID:n utan poster i eller tidigare det valda tidsintervallet visas inte.



  1. välj kolumn som sant/falskt om id finns i en annan tabell

  2. Laravel-appen på Azure:Åtkomst nekad för användaren 'azure'@'localhost'

  3. Sätt div i MYSQL-tärningen

  4. Grails databasmigrering på utplacerad server