Operatori di insieme
Indice
Capitolo 2
Gli operatori di insieme
SQL mette a disposizione degli operatori insiemistici, da applicare nella scrittura delle nostre interrogazioni. Tali operatori operano sul risultato di più select. Gli attributi interessati dagli operatori di insieme devono esser di tipo compatibile tra loro.
Gli operatori disponibili sono gli operatori di UNION (unione), INTERSECT (intersezione) e MINUS (differenza), il significato è analogo ai corrispondenti operatori dell’algebra insiemistica che adesso vedremo brevemente:
Teoria sugli operatori insiemistici
Unione:
Si definisce unione fra A e B l’insieme formato dagli elementi che appartengono almeno a uno dei due insiemi A e B.
L’unione fra gli insiemi A e B si indica scrivendo: A ∪ B
A = {G, 9, R} | A = {9, B} |
A ∪ B = {G, 9, R, B} |
Intersezione:
Si definisce intersezione fra A e B il sottoinsieme formato dagli elementi comuni agli insiemi A e B.
L’intersezione fra gli insiemi A e B si indica scrivendo: A ∩ B
A = {G, 9, R} | B = {9, B} |
A ∩ B = {9} |
Differenza fra due insiemi:
Si definisce differenza fra A e B, dati in questo ordine, il sottoinsieme formato dagli elementi di A che non appartengono a B.
La differenza fra gli insiemi A e B si indica scrivendo: A \ B.
A = {G, 9, R} | B = {9, B} |
A \ B = {G, R} |
Chiariti questi concetti basilari passiamo ora a vedere i corrispondenti operatori del linguaggio SQL:
Operatore UNION e UNION ALL:
L’operatore UNION restituisce il risultato di più query escludendo le righe duplicate, vediamo un esempio:
CALCIO | CALCETTO | |
NOME | NOME | |
MARINI | MARINI | |
BRAVO | BACCO | |
ROSSI | ROSSI | |
VERDI | DINI | |
MARRONI | MARRONI | |
GIALLI | FALCONE | |
GIANNINI | GIANNINI |
Vogliamo sapere quali persone giocano in una squadra o nell’altra:
SELECT NOME FROM CALCETTO
UNION
SELECT NOME FROM CALCIO;
NOME |
MARINI |
BACCO |
BRAVO |
ROSSI |
VERDI |
DINI |
MARRONI |
FALCONE |
GIALLI |
GIANNINI |
L’operatore UNION fornisce 10 nomi distinti estratti dalle due tabelle, se invece vogliamo vedere tutti i nomi che compaiono nelle due tabelle, duplicati inclusi, aggiungiamo ALL alla precedente espressione:
SELECT NOME FROM CALCETTO
UNION ALL
SELECT NOME FROM CALCIO;
NOME |
MARINI |
BACCO |
ROSSI |
DINI |
MARRONI |
FALCONE |
GIANNINI |
MARINI |
BRAVO |
ROSSI |
VERDI |
MARRONI |
GIALLI |
GIANNINI |
Operatore INTERSECT:
Restituisce l’intersezione (valori comuni a tutti gli insiemi coinvolti) del risultato delle query. La seguente istruzione SELECT mostra l’elenco dei giocatori che appartengono sia alla squadra di calcio che di calcetto. (Vedere le tabelle CALCIO e CALCETTO). Questo operatore non è implementato da Access.
SELECT NOME FROM CALCETTO
INTERSECT
SELECT NOME FROM CALCIO;
NOME |
MARINI |
ROSSI |
MARRONI |
GIANNINI |
Operatore MINUS (differenza):
Restituisce le righe della prima query che non sono presenti nella seconda. Questo operatore non è implementato da Access.
SELECT * FROM CALCIO
MINUS
SELECT * FROM CALCETTO;
NOME |
BRAVO |
VERDI |
GIALLI |
Altri operatori: IN e BETWEEN
Gli operatori IN e BETTWEEN forniscono una scorciatoia per quelle operazioni che possono essere svolte anche in altri modi. Ad esempio, per trovare tutti gli amici che vivono in provincia di Como, Pavia, e Bergamo,
AMICI | ||||
COGNOME | NOME | TELEFONO | PR | CAP |
ROSSI | MARIA | 0761 556632 | BG | 01023 |
VERDI | MARIA | 02 345622 | MI | 03456 |
MARRONI | ANTONIO | 0732 433388 | CO | 01255 |
BANFI | BARBY | 0722 114381 | BR | 03367 |
PERSIANI | LUCA | 0581 931522 | CA | 09941 |
MAZZA | ALBERTO | 0359 118267 | PV | 01944 |
BATTISTI | CHIARA | 0445 668193 | CT | 01042 |
possiamo usare le seguenti espressioni:
SELECT *FROM AMICIWHEREPR = ‘CO’ORPR = ‘PV’ORPR = ‘BG’; | SELECT *FROM AMICIWHERE PR IN (‘CO’, ‘PV’, ‘BG’); |
Il risultato che si ottiene per entrambe le espressioni è il seguente:
COGNOME | NOME | TELEFONO | PR | CAP |
ROSSI | MARIA | 23423 | BG | 01023 |
MARRONI | ANTONIO | 45567 | CO | 01255 |
MAZZA | ALBERTO | 567878 | PV | 01944 |
Facciamo ora un altro esempio:
PREZZO | |
ELEMENTO | PREZZO_INGROSSO |
POMODORI | 340 |
PATATE | 510 |
BANANE | 670 |
RAPE | 450 |
ARANCE | 890 |
MELE | 230 |
SELECT *FROM PREZZOWHERE PREZZO_INGROSSO >= 250ANDPREZZO_INGROSSO <= 750; | SELECT *FROM PREZZOWHERE PREZZO_INGROSSO BETWEEN250AND 750; |
Il risultato che si ottiene per entrambe le espressioni è il seguente:
ELEMENTO | PREZZO_INGROSSO |
POMODORI | 340 |
PATATE | 510 |
BANANE | 670 |
RAPE | 450 |
ESERCIZI (capitolo 2)
Utilizzare la tabella AMICI, qui riportata, per rispondere ai quesiti dove non è specificata altra tabella.
AMICI | ||
COGNOME | NOME | PR |
ROSSI | MARIA | BG |
VERDI | MARIA | MI |
MARRONI | ANTONIO | CO |
BANFI | BARBY | BR |
PERSIANI | LUCA | CA |
MAZZA | ALBERTO | PV |
BATTISTI | CHIARA | CT |
1) Scrivere una query per selezionare tutti i cognomi che iniziano con la lettera M.
2) Scrivere una query per selezionare gli amici che vivono in provincia di Bergamo (BG) e il cui nome è MARIA.
3) Quale è il risultato di questa query?
SELECT NOME, COGNOME
FROM AMICI
WHERE NOME = ‘MARIA’
OR COGNOME = ‘MAZZA’;
4) Quale è il risultato di questa query?
SELECT NOME, COGNOME
FROM AMICI
WHERE NOME = ‘MARIA’
AND COGNOME = ‘MAZZA’;
5) Quale scorciatoia potrebbe essere utilizzata in alternativa a WHERE A >= 10 AND A <= 30 ?
6) Scrivere una interrogazione che dalla tabella sottostante estrapoli il nome delle donne sposate
PERSONE | |||
ID_PERSONA | NOME | ID_CONIUGE | SESSO |
1 | ANTONIO | 12 | M |
12 | SILVIA | 1 | F |
2 | GIULIO | 7 | M |
3 | MARIA | F | |
6 | ROBERTA | 9 | F |
7 | ANTONELLA | 2 | F |
9 | ARTURO | 6 | M |
7) Scrivere una interrogazione che dalla tabella PERSONE estrapoli i nomi che iniziano per ‘A’ e finiscono per ‘O’.
8) Scrivere una interrogazione che dalla tabella PERSONE estrapoli i nomi in cui la quarta lettera sia una
‘O’.
9) Scrivere una interrogazione che ci visualizzi tutti i dati della tabella sottostante, più un colonna dal nome ‘PrezzoVendita’ in cui dovranno comparire i rispettivi prezzi della colonna PrezzoIngrosso ma aumentati del 15%
PREZZI | |
Elemento | PrezzoIngrosso |
Pomodori | 340 |
Patate | 510 |
Banane | 670 |
Rape | 450 |
Arance | 890 |
Mele | 230 |
10) Scrivere un interrogazione che inverta il segno dei valori presenti nella colonna PrezzoIngrosso della
tabella PREZZI.
Il database costituito dalle tabelle Cacciatori, Pescatori e Scalatori appartiene ad un circolo sportivo e contiene i nominativi degli iscritti a tale circolo. Gli iscritti sono raggruppati sulle tabelle in base allo sport che essi fanno. Chiaramente la stessa persona può fare più di uno sport e quindi comparire in più di una tabella. Per gli esercizi seguenti faremo riferimento a questo piccolo database.
CACCIATORI | PESCATORI | SCALATORI | |||||||
Codice | Nome | Codice | Nome | Codice | Nome | ||||
35 | ROSSI | 4 | ROSSI | 27 | NERI | ||||
27 | NERI | 77 | MANCINI | 11 | MARCA | ||||
12 | BINACHI | 49 | CRUCIANI | 1 | MICHELI | ||||
2 | BISCARDI | 11 | MARCA | 2 | BISCARDI |
11) Scrivere una query per visualizzare tutti i nominativi iscritti al circolo.
12) Scrivere una query per visualizzare i cacciatori che non siano anche scalatori.
13) Scrivere una query per visualizzare gli scalatori che non siano anche cacciatori.
14) Scrivere una query per visualizzare i pescatori che siano anche cacciatori.
15) Se dovessimo scrivere una query per visualizzare i cacciatori che siano anche pescatori potremmo
utilizzare la soluzione dell’esercizio N° 14?
16) Scrivere una query per visualizzare tutti i nominativi iscritti al circolo il cui nome finisce con ‘I’ e ci sia
almeno una ‘A’.
17) Scrivere una query per visualizzare tutti i nominativi iscritti al circolo il cui nome finisce con ‘I’ o ci sia
almeno una ‘A’.
SAlve, quindi non esiste una funzione come p.e. in Excel, che estragga alcuni caratteri a destra o sinistra?
Ho provato cn right(nome, 3) ma non lo riconosce
applicando l’add_months ad alcuni sql editor online appare il seguente messaggio di errore:
[“date” is not a recognized table hints option. If it is intended as a parameter to a table-valued function or to the CHANGETABLE function, ensure that your database compatibility mode is set to 90.]
SQL Editor utilizzati
https://rextester.com/l/sql_server_online_compiler
http://www.sqlfiddle.com/#!18/28da7/1
SELECT COUNT (*)
Buongiorno
FROM IMPIEGATO
WHERE DIPARTIMENTO = ‘PRODUZIONE’
genera il seguente errore:
“The data types text and varchar are incompatible in the equal to operator”.
Invece, sostituendo con WHERE DIPARTIMENTO LIKE ‘PRODUZIONE’, la query funziona.
Ho imparato alcune cose buone qui. Certamente merita il bookmarking per la rivisitazione.
Mi chiedo quanti sforzi hai impostato per creare questo tipo di fantastico sito informativo.
guida molto interessante grazie se ci fossero anche le istruzioni per creare la tabella sarebbe completa secondo me
Grazie per la guida. Semplice, interessante ed utile.
Vorremmo segnalare due cose. Un errore ed un dubbio.
Errore:
SELECT DIVISIONE, AVG(STIPENDIO)
FROM DIPENDENTI
HAVING AVG(STIPENDIO) > 2200000;
manca la “group by DIVISIONE” prima della HAVING.
Di conseguenza il dubbio sul punto 6.
HAVING non è necessario che venga posta dopo la clausola GROUP BY.
Sicuri?
Guida Molto utile, segnalo un errore nella query 9, capitolo 2, delle soluzioni:
PrezzoIngrosso è moltiplicato * 1,5 ma si chiedeva un aumento del 15%, ciò significa moltiplicare * 1,15
Grazie guida molto utile per imparare da 0.
Veramente complimenti, una guida dettagliata, semplice e adatta a tutti 🙂
FortyZone
Davvero complimenti ragazzi. La prima guida che per chi parte da zero è manna dal cielo…PERFETTA!!
nel punto 8 la soluzione non dovrebbe essere con HAVING MIN(IMPORTO) > 400 000; cioè: SELECT BENEFICIARI FROM ASSEGNI GROUP BY BENEFICIARIO HAVING MIN(IMPORTO) > 400 000;
un ottimo Manuale unico errore (se vogliamo chiamarlo cosi) i tipi di dati Char(5) number(5,2) cosa sono e come si usano
Complimenti ottimo sito! fatto davvero bene. Grazie!
ma come si crea il database?
È stata spiegato molto bene.