Oltre un singolo GROUP BY
Esegua aggregazioni a più livelli
Oltre un singolo GROUP BY è una lezione SQL Academy gratuita su CoddyKit. Questa è la lezione 1 di 4. Puoi leggere la lezione completa qui gratuitamente — poi esercitati direttamente nel browser con un editor di codice integrato e un tutor IA disponibile 24/7. Fa parte del percorso di apprendimento SQL Academy, e i tuoi progressi si sincronizzano tra il web e l'app CoddyKit. Il corso SQL Academy include 4 lezioni in totale.
Il limite di un singolo GROUP BY
Una clausola GROUP BY standard consente di aggregare le righe a un solo livello specifico, ad esempio le vendite totali per regione. Ma cosa succede se vuole anche i totali per categoria di prodotto e un totale complessivo, tutto nella stessa query?
Ripetere la query tre volte e usare UNION ALL funziona, ma rende il codice prolisso e lento. SQL offre tre potenti estensioni — GROUPING SETS, ROLLUP e CUBE — che risolvono elegantemente il problema in un'unica passata.
SELECT region, SUM(amount) AS total_sales
FROM sales
GROUP BY region;Impostazione della tabella di esempio
Nel corso di questa lezione useremo una semplice tabella sales, che registra ogni vendita indicando region, category e amount. Procediamo a crearla e popolarla, così ogni query successiva sarà comprensibile nel suo contesto.
CREATE TABLE sales (
id SERIAL PRIMARY KEY,
region TEXT,
category TEXT,
amount NUMERIC
);
INSERT INTO sales (region, category, amount) VALUES
('North', 'Electronics', 1200),
('North', 'Clothing', 800),
('South', 'Electronics', 950),
('South', 'Clothing', 600),
('East', 'Electronics', 1100),
('East', 'Clothing', 750);Che cosa sono i GROUPING SETS?
GROUPING SETS consente di definire più livelli di raggruppamento indipendenti all'interno di un'unica clausola GROUP BY. Ogni insieme nell'elenco produce il proprio gruppo di righe, come se si fossero scritte query separate e poi combinate con UNION ALL.
La sintassi è: GROUP BY GROUPING SETS ( (col1, col2), (col1), () ). L'insieme vuoto () rappresenta il totale complessivo di tutte le righe.
SELECT region, category, SUM(amount) AS total
FROM sales
GROUP BY GROUPING SETS (
(region, category),
(region),
()
);Lettura dell'output di GROUPING SETS
Quando si esegue una query con GROUPING SETS, le righe dei diversi livelli di raggruppamento vengono accodate. Le colonne che non fanno parte di un determinato insieme appaiono come NULL in quella riga.
Ad esempio, una riga appartenente all'insieme (region) avrà NULL nella colonna category, a indicare che il totale comprende tutte le categorie di quella regione. La riga del totale complessivo (insieme vuoto) ha NULL sia in region sia in category.
SELECT
COALESCE(region, 'ALL REGIONS') AS region,
COALESCE(category, 'ALL CATEGORIES') AS category,
SUM(amount) AS total
FROM sales
GROUP BY GROUPING SETS (
(region, category),
(region),
()
)
ORDER BY region NULLS LAST, category NULLS LAST;Introduzione a ROLLUP
ROLLUP è un'abbreviazione per una gerarchia comune di insiemi di raggruppamento. Date le colonne (A, B), ROLLUP(A, B) genera automaticamente gli insiemi: (A, B), (A) e ().
È perfetto per dati gerarchici, ad esempio year, month e day, oppure region e category. Il numero di insiemi prodotti è sempre n + 1, dove n è il numero di colonne elencate.
-- ROLLUP(region, category) is equivalent to:
-- GROUPING SETS ( (region, category), (region), () )
SELECT region, category, SUM(amount) AS total
FROM sales
GROUP BY ROLLUP(region, category)
ORDER BY region NULLS LAST, category NULLS LAST;ROLLUP con tre livelli
L'aggiunta di una terza colonna a ROLLUP estende la gerarchia di un ulteriore livello. ROLLUP(A, B, C) genera quattro insiemi: (A, B, C), (A, B), (A) e ().
Nell'esempio seguente, year è il livello più esterno e category quello più granulare. La query produce subtotali a ogni passaggio della gerarchia, oltre a una riga del totale complessivo.
SELECT
year,
region,
category,
SUM(amount) AS total
FROM (
VALUES
(2024, 'North', 'Electronics', 1200),
(2024, 'North', 'Clothing', 800),
(2024, 'South', 'Electronics', 950),
(2025, 'North', 'Electronics', 1400),
(2025, 'South', 'Clothing', 700)
) AS t(year, region, category, amount)
GROUP BY ROLLUP(year, region, category)
ORDER BY year NULLS LAST, region NULLS LAST, category NULLS LAST;Introduzione a CUBE
CUBE è ancora più completo di ROLLUP. Date n colonne, genera tutte le 2^n combinazioni possibili degli insiemi di raggruppamento, incluso il totale complessivo.
Per CUBE(region, category), gli insiemi prodotti sono: (region, category), (region), (category) e () — quattro insiemi in totale. È utile quando servono totali trasversali in ogni direzione, non soltanto lungo una singola gerarchia.
-- CUBE(region, category) produces:
-- GROUPING SETS ( (region,category), (region), (category), () )
SELECT region, category, SUM(amount) AS total
FROM sales
GROUP BY CUBE(region, category)
ORDER BY region NULLS LAST, category NULLS LAST;CUBE o ROLLUP: quale usare?
La scelta dipende dal fatto che le dimensioni abbiano o meno una gerarchia naturale:
- Utilizzi ROLLUP quando le colonne sono gerarchiche, ad esempio country, city e store. I subtotali risalgono soltanto lungo un percorso.
- Utilizzi CUBE quando le colonne sono dimensioni indipendenti, ad esempio region e category, e desidera ogni possibile combinazione.
- Utilizzi GROUPING SETS quando serve il pieno controllo e né ROLLUP né CUBE soddisfano esattamente i requisiti.
La funzione GROUPING()
Poiché NULL può indicare sia un valore mancante effettivo sia un segnaposto di raggruppamento, SQL mette a disposizione la funzione GROUPING(). Restituisce 1 quando la colonna fa parte di una riga di superaggregazione (segnaposto) e 0 quando la colonna è stata effettivamente usata per il raggruppamento.
In questo modo è possibile distinguere un NULL reale nella colonna region da una riga di subtotale che comprende tutte le regioni.
SELECT
region,
category,
SUM(amount) AS total,
GROUPING(region) AS is_region_subtotal,
GROUPING(category) AS is_category_subtotal
FROM sales
GROUP BY CUBE(region, category)
ORDER BY region NULLS LAST, category NULLS LAST;Uso di GROUPING() per etichettare le righe
Un modello comune consiste nel combinare GROUPING() con un'espressione CASE per produrre etichette leggibili invece di valori NULL non elaborati. In questo modo l'output di una query ROLLUP o CUBE risulta molto più facile da leggere nei report.
SELECT
CASE GROUPING(region)
WHEN 1 THEN 'Grand Total'
ELSE region
END AS region_label,
CASE GROUPING(category)
WHEN 1 THEN 'All Categories'
ELSE category
END AS category_label,
SUM(amount) AS total
FROM sales
GROUP BY ROLLUP(region, category)
ORDER BY GROUPING(region), region, GROUPING(category), category;Combinare colonne fisse con ROLLUP
È possibile combinare colonne regolari di GROUP BY con ROLLUP o CUBE nella stessa clausola. Le colonne elencate al di fuori di ROLLUP(...) sono sempre incluse in ogni insieme di raggruppamento: non vengono mai sottoposte a ROLLUP.
Nella query seguente, year è una colonna di raggruppamento fissa, mentre region e category partecipano a ROLLUP. Di conseguenza, si ottengono subtotali per ogni year, non un unico totale per tutti gli year.
SELECT
2024 AS year,
region,
category,
SUM(amount) AS total
FROM sales
GROUP BY 2024, ROLLUP(region, category)
ORDER BY region NULLS LAST, category NULLS LAST;Verifica rapida
Metta alla prova la propria comprensione di GROUPING SETS, ROLLUP e CUBE.
Riepilogo — oltre un singolo GROUP BY
In questa lezione ha imparato a usare tre potenti estensioni di SQL, che consentono di produrre più livelli di aggregazione in un'unica query:
- GROUPING SETS — offre il pieno controllo manuale e consente di elencare esattamente le combinazioni necessarie.
- ROLLUP — è ideale per le gerarchie: risale dal livello più dettagliato fino al totale complessivo.
- CUBE — genera ogni possibile combinazione trasversale delle dimensioni elencate.
Ha inoltre imparato che GROUPING() distingue i valori NULL effettivi dalle righe segnaposto di superaggregazione e che i modelli CASE GROUPING(...) producono un output pulito e leggibile nei report.
Questi strumenti sono indispensabili quando servono riepiloghi multidimensionali: report in stile pivot, dashboard e query di data warehouse fanno ampio affidamento su di essi.
Impara SQL con un tutor IA — gratis
Scrivi ed esegui vero codice nel tuo browser, ricevi aiuto istantaneo da un tutor IA disponibile 24/7, e riprendi da dove hai lasciato sul web o nell'app.
- Corsi
- 46
- Lezioni
- 183
Domande Frequenti
La lezione «Oltre un singolo GROUP BY» è gratuita?
Sì — il testo completo di «Oltre un singolo GROUP BY» è gratuito qui sul web. Per esercitarvi in modo interattivo (un editor di codice integrato e un tutor IA 24/7) e sbloccare il resto del corso SQL Academy, passa a CoddyKit PRO. Il corso SQL Academy include 4 lezioni in totale.
Cosa imparerò in «Oltre un singolo GROUP BY»?
Esegua aggregazioni a più livelli Eserciti SQL Academy con codice pratico che esegui direttamente nel browser, e un tutor IA 24/7 risponde alle tue domande mentre lavori sulla lezione.
Ho bisogno di esperienza per iniziare SQL Academy?
Non è richiesta alcuna esperienza precedente. SQL Academy su CoddyKit è strutturato per principianti e studenti avanzati, quindi puoi iniziare da qui o dall'inizio e procedere al tuo ritmo. Questa è la lezione 1 di 4.
Quanto tempo richiede la lezione «Oltre un singolo GROUP BY»?
La maggior parte delle lezioni CoddyKit richiede circa 5–10 minuti. Ogni lezione è breve e interattiva, quindi fai progressi costanti e riprendi esattamente da dove hai lasciato su web e app.
Posso scrivere ed eseguire codice in questa lezione SQL Academy?
Sì. Ogni lezione SQL Academy include un editor di codice integrato, quindi scrivi ed esegui codice reale direttamente nel tuo browser e ricevi feedback istantaneo dall'IA — nessuna configurazione locale necessaria.
Tutte le lezioni di questo corso
- Oltre un singolo GROUP BY
- ROLLUP per i subtotali
- CUBE per tutte le combinazioni
- GROUPING SETS spiegati