GROUPING SETS ist eine Erweiterung der SQL-Klausel GROUP BY, mit der mehrere Gruppierungsebenen in einer Abfrage erzeugt werden. Statt mehrere GROUP BY-Abfragen per UNION ALL zu verbinden, listet man die gewünschten Ebenen einfach als Menge auf — die Datenbank liefert alle Zusammenfassungen in einem Durchlauf.
Das Grundprinzip
Die Syntax steht hinter GROUP BY und nennt jede Gruppierungsebene als eigenes Tupel in Klammern. Der leere Klammerausdruck () steht für die Gesamtsumme über alle Zeilen:
SELECT jahr, kategorie, SUM(umsatz) AS summe
FROM verkauf
GROUP BY GROUPING SETS ((jahr, kategorie), (jahr), ());
Die Abfrage liefert drei Ebenen in einem Ergebnis: Umsätze je Jahr und Kategorie, je Jahr sowie die Gesamtsumme. Ohne GROUPING SETS bräuchte man dafür drei einzelne Abfragen, die man anschließend mit UNION ALL zusammensetzt — das ist langsamer, weil die Tabelle mehrfach gelesen wird.
Der Vorteil gegenüber UNION ALL
GROUPING SETS liest die Tabelle nur einmal und bildet alle gewünschten Ebenen in einem Zug. Gerade bei großen Tabellen spart das erheblich Zeit. Außerdem bleibt die Abfrage lesbar: Die gewünschten Ebenen stehen explizit in der Klausel, statt über viele SELECT-Blöcke verteilt zu sein.
NULL-Werte unterscheiden mit GROUPING()
In den zusammengefassten Zeilen steht in den nicht gruppierten Spalten NULL. Um echte Daten-NULL von diesen Super-Aggregat-NULL zu unterscheiden, gibt es die GROUPING()-Funktion: GROUPING(jahr) = 1 bedeutet, dass der NULL-Wert aus der Zusammenfassung stammt und nicht aus den Daten.
Verfügbarkeit
GROUPING SETS ist Teil des SQL-Standards (SQL:1999) und wird von PostgreSQL (ab 9.5), SQL Server, Oracle sowie BigQuery, Snowflake und Redshift nativ unterstützt. MySQL kennt nur GROUP BY ... WITH ROLLUP; GROUPING SETS lassen sich dort über UNION ALL mehrerer Abfragen nachbilden.
Einordnung
GROUPING SETS gehört zur Detail-Ebene der GROUP BY-Auswertung: ROLLUP erzeugt hierarchische Zwischensummen, CUBE alle Kombinationen, GROUPING SETS genau die selbst gewählten Ebenen. Mit HAVING lassen sich die fertigen Gruppen anschließend filtern.
Verwandte Grundlagen: SQL GROUP BY, SQL ROLLUP, SQL CUBE, SQL HAVING.