[successivo] [precedente] [inizio] [fine] [indice generale] [indice ridotto] [indice analitico] [volume] [parte]


Capitolo 624.   Aggregazioni

L'aggregazione è una forma di interrogazione attraverso cui si ottengono risultati riepilogativi del contenuto di una relazione, nel suo complesso o a gruppi di tuple. Per questo si utilizzano delle funzioni speciali al posto dell'espressione che esprime gli attributi del risultato. Queste funzioni restituiscono un solo valore e come tali concorrono a creare un'unica tupla.

Tabella 624.1. Alcune funzioni aggreganti riconosciute da SQLite.

Funzione Descrizione
COUNT(x)
Restituisce il numero di tuple, nel gruppo, per le quali l'espressione x restituisce un valore diverso da NULL.
COUNT(*)
Restituisce il numero di tuple esistenti nel gruppo.
AVG(x)
Restituisce la media, nel gruppo di tuple, dei valori che ottiene l'espressione x, escludendo NULL e considerando i valori non numerici pari a zero.
MIN(x)
MAX(x)
Restituisce il valore minimo o massimo, nel gruppo di tuple, dei valori che ottiene l'espressione x, escludendo NULL e considerando i valori non numerici pari a zero.
SUM(x)
Restituisce la somma, nel gruppo di tuple, dei valori che ottiene l'espressione x, escludendo NULL e considerando i valori non numerici pari a zero.

La forma che assume l'istruzione SELECT quando si usano le aggregazioni e tipicamente quella seguente:

SELECT specificazione_dell'attributo_1[,...specificazione_dell'attributo_n]
    FROM specificazione_della_relazione_1[,...specificazione_della_relazione_n]
    [WHERE condizione]
    [GROUP BY attributo_1[,...]]

In pratica, le funzioni aggreganti vanno usate nell'elenco che descrive gli attributi. Se non si usa l'opzione GROUP BY, il gruppo di tuple di riferimento comprende tutte le tuple della relazione o della congiunzione (di relazioni). Se si specifica l'opzione GROUP BY, le tuple vengono raggruppate in base all'uguaglianza degli attributi indicati come argomento di tale opzione. In pratica:

  1. la relazione ottenuta dall'istruzione SELECT...FROM viene filtrata dalla condizione WHERE;

  2. la relazione risultante viene riordinata in modo da raggruppare le tuple in cui i contenuti degli attributi elencati dopo l'opzione GROUP BY sono uguali;

  3. su questi gruppi di tuple vengono valutate le funzioni di aggregazione.

624.1   Aggregazioni banali

Per prendere un po' di dimestichezza con le aggregazioni, conviene usare il programma sqlite3 in modo interattivo e fare qualche piccolo esperimento:

sqlite3 mag.db[Invio]

SQLite version ...
Enter ".help" for instructions

sqlite> .headers on[Invio]

sqlite> .mode column[Invio]

Si vogliono contare le tuple della relazione Movimenti:

sqlite> SELECT COUNT(*) FROM Movimenti;[Invio]

10

Si vogliono contare i movimenti per ogni tipo di articolo:

sqlite> SELECT Articolo, COUNT(*) FROM Movimenti GROUP BY Articolo;[Invio]

Articolo    COUNT(*)
----------  ----------
2           2
102         3
401         3
601         2

Si vuole conoscere la quantità esistente di ogni articolo (si usa la vista MovimentiExtra, che offre l'attributo QuantitaAlgebrica):

sqlite> SELECT Articolo, SUM(QuantitaAlgebrica)[Invio]

   ...>     FROM MovimentiExtra GROUP BY Articolo;[Invio]

Articolo    SUM(QuantitaAlgebrica)
----------  ----------------------
2           9000
102         800
401         700
601         1000

Si vuole conoscere la quantità esistente di ogni articolo in magazzino e il valore (il valore viene calcolato a partire da quello medio, moltiplicato per la quantità algebrica):

sqlite> SELECT Articolo, SUM(QuantitaAlgebrica),[Invio]

    ...>       SUM(QuantitaAlgebrica*ValoreUnitario)[Invio]

    ...>     FROM MovimentiExtra GROUP BY Articolo;[Invio]

Articolo    SUM(QuantitaAlgebrica)  SUM(QuantitaAlgebrica*ValoreUnitario)
----------  ----------------------  -------------------------------------
2           9000                    90
102         800                     160
401         700                     140
601         1000                    500

Si vuole conoscere la quantità esistente di ogni articolo in magazzino e il costo medio, determinato dividendo il valore complessivo per la quantità esistente:

sqlite> SELECT Articolo,[Invio]

sqlite>        SUM(QuantitaAlgebrica),[Invio]

sqlite>        SUM(QuantitaAlgebrica*ValoreUnitario)/\
  \SUM(QuantitaAlgebrica)
[Invio]

sqlite>        FROM MovimentiExtra GROUP BY Articolo;[Invio]

Articolo    SUM(QuantitaAlgebrica)  SUM(QuantitaAlgebrica*ValoreUnitario)/SUM(QuantitaAlgebrica)
----------  ----------------------  ------------------------------------------------------------
2           9000                    0.01
102         800                     0.2
401         700                     0.2
601         1000                    0.5

sqlite> .quit[Invio]

624.2   Verifica sulla creazione della vista «SituazioneMagazzino»

Si vuole realizzare la vista SituazioneMagazzino che, in questa verifica, si limiti a mostrare poche informazioni riepilogative sullo stato del magazzino.

Si realizzi il file vista-situazione-magazzino-1.sql, seguendo lo scheletro che viene proposto, per far sì che la vista SituazioneMagazzino contenga gli attributi seguenti:

  1. Codice, corrispondente al codice articolo della relazione Movimenti o della vista MovimentiExtra;

  2. Articolo, corrispondente alla descrizione dell'articolo, come indicato nella relazione Articoli;

  3. Esistenza, corrispondente alla somma algebrica dei carichi, come si ottiene dalla vista MovimentiExtra.

Figura 624.8. Scheletro del file vista-situazione-magazzino-1.sql, da completare.

-- Vista "SituazioneMagazzino"
-- Esercizio di: cognome nome classe
-- Data: data
-- File: vista-situazione-magazzino-1.sql

CREATE VIEW SituazioneMagazzino AS
    SELECT MovimentiExtra.Articolo               AS Codice,
           ...
           ...
           FROM ...
           WHERE MovimentiExtra.Articolo = Articoli.Articolo
           GROUP BY MovimentiExtra.Articolo;

Per eseguire il file vista-situazione-magazzino-1.sql, si agisce come sempre:

sqlite3 mag.db < vista-situazione-magazzino-1.sql[Invio]

Se la creazione della vista produce degli errori, occorre eliminare la vista e, dopo la correzione del file vista-situazione-magazzino-1.sql, si può ritentare.

Quando si è consapevoli di avere creato correttamente la vista SituazioneMagazzino, la si può interrogare come se fosse una relazione normale:

sqlite3 mag.db[Invio]

SQLite version ...
Enter ".help" for instructions

sqlite> .headers on[Invio]

sqlite> .mode column[Invio]

sqlite> SELECT * FROM SituazioneMagazzino;[Invio]

Si dovrebbe ottenere il listato seguente:

Codice      Articolo                                Esistenza 
----------  --------------------------------------  ----------
2           Dischetti da 9 cm 1440 Kibyte colorati  9000      
102         CD-R 52x                                800       
401         DVD+R 8x                                700       
601         DVD+RW 8x                               1000      

Se tutto funziona regolarmente, si consegni per la valutazione la stampa del file vista-situazione-magazzino-1.sql.

624.3   Verifica sulla creazione della vista «SituazioneMagazzino»

Si vuole estendere la vista SituazioneMagazzino, già realizzata in parte nella verifica precedente; pertanto, in questa verifica si modifica il file vista-situazione-magazzino-1.sql Salvandolo con il nome vista-situazione-magazzino-2. Si vogliono ottenere gli attributi seguenti:

  1. Codice, corrispondente al codice articolo della relazione Movimenti o della vista MovimentiExtra;

  2. Articolo, corrispondente alla descrizione dell'articolo, come indicato nella relazione Articoli;

  3. ScortaMin, corrispondente alla scorta minima, come contenuto nella relazione Articoli;

  4. Esistenza, corrispondente alla somma algebrica dei carichi, come si ottiene dalla vista MovimentiExtra;

  5. Valore, corrispondente al valore complessivo di ogni articolo (come mostrato negli esempi prima di queste verifiche).

Figura 624.11. Scheletro del file vista-situazione-magazzino-2.sql, da completare.

-- Vista "SituazioneMagazzino"
-- Esercizio di: cognome nome classe
-- Data: data
-- File: vista-situazione-magazzino-2.sql

CREATE VIEW SituazioneMagazzino AS
    SELECT MovimentiExtra.Articolo               AS Codice,
           ...
           ...
           FROM ...
           WHERE MovimentiExtra.Articolo = Articoli.Articolo
           GROUP BY MovimentiExtra.Articolo;

Prima di poter eseguire questo file con la base di dati, occorre eliminare la vista SituazioneMagazzino, che già dovrebbe esistere. Si ricorda che per eliminare una vista si utilizza l'istruzione DROP VIEW e che conviene intervenire con il programma sqlite3 in modo interattivo.

Per eseguire il file vista-situazione-magazzino-2.sql, si agisce come sempre:

sqlite3 mag.db < vista-situazione-magazzino-2.sql[Invio]

Se la creazione della vista produce degli errori, occorre eliminare la vista e, dopo la correzione del file vista-situazione-magazzino-2.sql, si può ritentare.

Quando si è consapevoli di avere creato correttamente la vista SituazioneMagazzino, la si può interrogare come se fosse una relazione normale:

sqlite3 mag.db[Invio]

SQLite version ...
Enter ".help" for instructions

sqlite> .headers on[Invio]

sqlite> .mode column[Invio]

sqlite> SELECT * FROM SituazioneMagazzino;[Invio]

Si dovrebbe ottenere il listato seguente:

Codice      Articolo                                ScortaMin   Esistenza   Valore    
----------  --------------------------------------  ----------  ----------  ----------
2           Dischetti da 9 cm 1440 Kibyte colorati  500         9000        90        
102         CD-R 52x                                500         800         160       
401         DVD+R 8x                                200         700         140       
601         DVD+RW 8x                               200         1000        500       

Se tutto funziona regolarmente, si consegni per la valutazione la stampa del file vista-situazione-magazzino-2.sql.

624.4   Verifica sulla creazione della vista «SituazioneMagazzino»

Si vuole estendere la vista SituazioneMagazzino, già realizzata in parte nella verifica precedente, in modo ottenere anche il costo medio; pertanto, in questa verifica si modifica il file vista-situazione-magazzino-2.sql salvandolo con il nome vista-situazione-magazzino-3.sql. Si vogliono ottenere gli attributi seguenti:

  1. Codice, corrispondente al codice articolo della relazione Movimenti o della vista MovimentiExtra;

  2. Articolo, corrispondente alla descrizione dell'articolo, come indicato nella relazione Articoli;

  3. ScortaMin, corrispondente alla scorta minima, come contenuto nella relazione Articoli;

  4. Esistenza, corrispondente alla somma algebrica dei carichi, come si ottiene dalla vista MovimentiExtra;

  5. Valore, corrispondente al valore complessivo di ogni articolo (come mostrato negli esempi prima di queste verifiche);

  6. CostoMedio, corrispondente al valore complessivo di ogni articolo, diviso la quantità esistente (come mostrato negli esempi prima di queste verifiche).

Figura 624.14. Scheletro del file vista-situazione-magazzino-3.sql, da completare.

-- Vista "SituazioneMagazzino"
-- Esercizio di: cognome nome classe
-- Data: data
-- File: vista-situazione-magazzino-3.sql

CREATE VIEW SituazioneMagazzino AS
    SELECT MovimentiExtra.Articolo               AS Codice,
           ...
           ...
           FROM ...
           WHERE MovimentiExtra.Articolo = Articoli.Articolo
           GROUP BY MovimentiExtra.Articolo;

Prima di poter eseguire questo file con la base di dati, occorre eliminare la vista SituazioneMagazzino, che già dovrebbe esistere. Si ricorda che per eliminare una vista si utilizza l'istruzione DROP VIEW e che conviene intervenire con il programma sqlite3 in modo interattivo.

Per eseguire il file vista-situazione-magazzino-3.sql, si agisce come sempre:

sqlite3 mag.db < vista-situazione-magazzino-3.sql[Invio]

Se la creazione della vista produce degli errori, occorre eliminare la vista e, dopo la correzione del file vista-situazione-magazzino-3.sql, si può ritentare.

Quando si è consapevoli di avere creato correttamente la vista SituazioneMagazzino, la si può interrogare come se fosse una relazione normale:

sqlite3 mag.db[Invio]

SQLite version ...
Enter ".help" for instructions

sqlite> .headers on[Invio]

sqlite> .mode column[Invio]

sqlite> SELECT * FROM SituazioneMagazzino;[Invio]

Si dovrebbe ottenere il listato seguente:

Codice Articolo                                ScortaMin Esistenza Valore CostoMedio
------ --------------------------------------  --------- --------- ------ ----------
2      Dischetti da 9 cm 1440 Kibyte colorati  500       9000      90     0.01      
102    CD-R 52x                                500       800       160    0.2       
401    DVD+R 8x                                200       700       140    0.2       
601    DVD+RW 8x                               200       1000      500    0.5       

Se tutto funziona regolarmente, si consegni per la valutazione la stampa del file vista-situazione-magazzino-3.sql.

624.5   Conclusione

Prima di passare al capitolo successivo, si deve riprendere il file magazzino.sql e vi si deve aggiungere l'istruzione per la creazione della vista SituazioneMagazzino, come realizzato nel'ultima verifica appena conclusa.

Una volta aggiornato il file magazzino.sql come descritto, si deve cancellare il file mag.db e ricreare a partire dalle istruzioni contenute nel file magazzino.sql:

sqlite3 mag.db < magazzino.sql[Invio]

Se vengono segnalati degli errori, occorre correggere il file magazzino.sql, cancellare nuovamente il file mag.db, quindi si deve ripetere l'operazione. La base di dati contenuta nel file mag.db, viene usata nel capitolo successivo e non si può proseguire se non si riesce a ricrearla correttamente.

Appunti di informatica libera 2007.02 --- Copyright © 2000-2007 Daniele Giacomini -- <daniele (ad) swlibero·org>


Dovrebbe essere possibile fare riferimento a questa pagina anche con il nome aggregazioni.htm

[successivo] [precedente] [inizio] [fine] [indice generale] [indice ridotto] [indice analitico]

Valid ISO-HTML!

CSS validator!