PostgreSQL
 sql >> Datenbank >  >> RDS >> PostgreSQL

Generate_series in Postgres aus Start- und Enddatum in einer Tabelle

Sie brauchen dafür keinen CTE, das wäre teurer als nötig.
Und Sie müssen nicht auf timestamp umwandeln , das Ergebnis ist bereits ist vom Datentyp timestamp wenn Sie timestamp eingeben Typen zu generate_series() . Details hier:

  • Generieren von Zeitreihen zwischen zwei Daten in PostgreSQL

In Postgres 9.3 oder später können Sie ein LATERAL verwenden beitreten:

SELECT to_char(ts, 'YYYY-MM-DD HH24') AS formatted_ts
FROM  (
   SELECT min(start_timestamp) as first_date
        , max(start_timestamp) as last_date
   FROM   header_table
   ) h
  , generate_series(h.first_date, h.last_date, interval '1 hour') g(ts);

Optional mit to_char() um das Ergebnis als Text in dem von Ihnen genannten Format zu erhalten.

Dies funktioniert in beliebigen Postgres-Version:

SELECT generate_series(min(start_timestamp)
                     , max(start_timestamp)
                     , interval '1 hour') AS ts
FROM   header_table;

Typischerweise etwas schneller.
Aufruf von Set-Returning-Funktionen im SELECT list ist eine Nicht-Standard-SQL-Funktion und wird von einigen verpönt. Außerdem gab es Verhaltensauffälligkeiten (allerdings nicht für diesen einfachen Fall), die schließlich in Postgres 10 behoben wurden. Siehe:

  • Was ist das erwartete Verhalten für mehrere Set-zurückgebende Funktionen in der SELECT-Klausel?

Hinweis ein subtiler Unterschied in NULL Handhabung:

Das Äquivalent von

max(start_timestamp)

erhält man mit

ORDER BY start_timestamp DESC NULLS LAST
LIMIT 1

Ohne NULLS LAST NULL-Werte kommen zuerst in absteigender Reihenfolge (wenn es kann NULL-Werte in start_timestamp sein ). Sie würden NULL für last_date erhalten und Ihre Abfrage wäre leer.

Einzelheiten:

  • Warum kommen NULL-Werte zuerst, wenn DESC in einer PostgreSQL-Abfrage bestellt wird?