

Le traduzioni sono generate tramite traduzione automatica. In caso di conflitto tra il contenuto di una traduzione e la versione originale in Inglese, quest'ultima prevarrà.

# Clausola JOIN
<a name="join-clause"></a>

Una clausola SQL JOIN viene utilizzata per combinare i dati di due o più tabelle in base a campi comuni. I risultati potrebbero cambiare o meno a seconda del metodo di join specificato. Gli outer join sinistro e destro mantengono i valori da una delle tabelle unite quando non viene trovata alcuna corrispondenza nell'altra tabella. 

La combinazione del tipo JOIN e della condizione di join determina quali righe vengono incluse nel set di risultati finale. Le clausole SELECT e WHERE controllano quindi quali colonne vengono restituite e come vengono filtrate le righe. Comprendere i diversi tipi di JOIN e come utilizzarli in modo efficace è un'abilità fondamentale in SQL, perché consente di combinare i dati di più tabelle in modo flessibile e potente.

## Sintassi
<a name="join-clause-syntax"></a>

```
SELECT column1, column2, ..., columnn
FROM table1
join_type table2
ON table1.column = table2.column;
```

## Parameters
<a name="join-clause-parameters"></a>

 *SELEZIONA colonna1, colonna2,..., colonnaN*   
Le colonne da includere nel set di risultati. È possibile selezionare le colonne da una o entrambe le tabelle coinvolte nel JOIN. 

 *DALLA tabella 1*   
La prima tabella (a sinistra) dell'operazione JOIN.

 *[JOIN \$1 INNER JOIN \$1 LEFT [OUTER] JOIN \$1 RIGHT [OUTER] JOIN \$1 [OUTER] JOIN COMPLETO] table2:*   
Il tipo di JOIN da eseguire. JOIN o INNER JOIN restituisce solo le righe con valori corrispondenti in entrambe le tabelle.   
LEFT [OUTER] JOIN restituisce tutte le righe della tabella di sinistra, con le righe corrispondenti della tabella di destra.   
RIGHT [OUTER] JOIN restituisce tutte le righe della tabella di destra, con le righe corrispondenti della tabella di sinistra.   
FULL [OUTER] JOIN restituisce tutte le righe di entrambe le tabelle, indipendentemente dal fatto che esista una corrispondenza o meno.   
CROSS JOIN crea un prodotto cartesiano delle righe delle due tabelle.

 *ON table1.column = table2.column*   
La condizione di unione, che specifica come vengono abbinate le righe nelle due tabelle. La condizione di unione può essere basata su una o più colonne.

 *Condizione WHERE:*   
Una clausola facoltativa che può essere utilizzata per filtrare ulteriormente il set di risultati, in base a una condizione specificata. 

## Esempio
<a name="Join_examples"></a>

Di seguito è riportato un esempio di join tra due tabelle con la clausola USING. In questo caso, le colonne listid e eventid vengono utilizzate come colonne di join. I risultati sono limitati a cinque righe.

```
select listid, listing.sellerid, eventid, listing.dateid, numtickets
from listing join sales
using (listid, eventid)
order by 1
limit 5;

listid | sellerid | eventid | dateid | numtickets
-------+----------+---------+--------+-----------
1      | 36861    | 7872    | 1850   | 10
4      | 8117     | 4337    | 1970   | 8
5      | 1616     | 8647    | 1963   | 4
5      | 1616     | 8647    | 1963   | 4
6      | 47402    | 8240    | 2053   | 18
```

# Tipi di join
<a name="join-types"></a>

## INNER
<a name="inner-join"></a>

Questo è il tipo di join predefinito. Restituisce le righe con valori corrispondenti in entrambi i riferimenti alla tabella. 

L'INNER JOIN è il tipo di join più comune utilizzato in SQL. È un modo efficace per combinare i dati di più tabelle in base a una colonna o un set di colonne comune. 

**Sintassi:**

```
SELECT column1, column2, ..., columnn
FROM table1
INNER JOIN table2
ON table1.column = table2.column;
```

La seguente query restituirà tutte le righe in cui è presente un valore customer\$1id corrispondente tra le tabelle clienti e ordini. Il set di risultati conterrà le colonne customer\$1id, name, order\$1id e order\$1date.

```
SELECT customers.customer_id, customers.name, orders.order_id, orders.order_date
FROM customers
INNER JOIN orders
ON customers.customer_id = orders.customer_id;
```

La seguente query è un inner join (senza la parola chiave JOIN) tra la tabella LISTING e la tabella SALES, in cui il LISTID della tabella LISTING è compreso tra 1 e 5. Questa query corrisponde ai valori della colonna LISTID nella tabella LISTING (la tabella di sinistra) e SALES (la tabella di destra). I risultati mostrano che LISTID 1, 4 e 5 corrispondono ai criteri.

```
select listing.listid, sum(pricepaid) as price, sum(commission) as comm
from listing, sales
where listing.listid = sales.listid
and listing.listid between 1 and 5
group by 1
order by 1;

listid | price  |  comm
-------+--------+--------
     1 | 728.00 | 109.20
     4 |  76.00 |  11.40
     5 | 525.00 |  78.75
```

Di seguito è riportato un esempio di inner join con la clausola ON. In questo caso, le righe NULL non vengono restituite.

```
select listing.listid, sum(pricepaid) as price, sum(commission) as comm
from sales join listing
on sales.listid=listing.listid and sales.eventid=listing.eventid
where listing.listid between 1 and 5
group by 1
order by 1;

listid | price  |  comm
-------+--------+--------
     1 | 728.00 | 109.20
     4 |  76.00 |  11.40
     5 | 525.00 |  78.75
```

La seguente query è un inner join di due sottoquery della clausola FROM. La query trova il numero di biglietti venduti e invenduti per diverse categorie di eventi (concerti e spettacoli). Queste sottoquery della clausola FROM sono sottoquery *table* e possono restituire più colonne e righe.

```
select catgroup1, sold, unsold
from
(select catgroup, sum(qtysold) as sold
from category c, event e, sales s
where c.catid = e.catid and e.eventid = s.eventid
group by catgroup) as a(catgroup1, sold)
join
(select catgroup, sum(numtickets)-sum(qtysold) as unsold
from category c, event e, sales s, listing l
where c.catid = e.catid and e.eventid = s.eventid
and s.listid = l.listid
group by catgroup) as b(catgroup2, unsold)

on a.catgroup1 = b.catgroup2
order by 1;

catgroup1 |  sold  | unsold
----------+--------+--------
Concerts  | 195444 |1067199
Shows     | 149905 | 817736
```

## SINISTRA [ESTERNO]
<a name="left-outer-join"></a>

Restituisce tutti i valori dal riferimento alla tabella sinistra e i valori corrispondenti dal riferimento alla tabella destra oppure aggiunge NULL se non c'è corrispondenza. Viene anche chiamato *left* outer join. 

Restituisce tutte le righe della tabella sinistra (prima) e le righe corrispondenti della tabella destra (seconda). Se non c'è alcuna corrispondenza nella tabella di destra, il set di risultati conterrà valori NULL per le colonne della tabella di destra. La parola chiave OUTER può essere omessa e il join può essere scritto semplicemente come LEFT JOIN. L'opposto di un LEFT OUTER JOIN è un RIGHT OUTER JOIN, che restituisce tutte le righe della tabella di destra e le righe corrispondenti della tabella di sinistra.

**Sintassi:**

```
SELECT column1, column2, ..., columnn
FROM table1
LEFT [OUTER] JOIN table2
ON table1.column = table2.column;
```

La seguente query restituirà tutte le righe della tabella clienti, insieme alle righe corrispondenti della tabella ordini. Se un cliente non ha ordini, il set di risultati includerà comunque le informazioni del cliente, con valori NULL per le colonne order\$1id e order\$1date.

```
SELECT customers.customer_id, customers.name, orders.order_id, orders.order_date
FROM customers
LEFT OUTER JOIN orders
ON customers.customer_id = orders.customer_id;
```

La seguente query è un outer join. Gli outer join sinistro e destro mantengono i valori da una delle tabelle unite quando non viene trovata alcuna corrispondenza nell'altra tabella. Le tabelle sinistra e destra sono la prima e la seconda tabella elencate nella sintassi. I valori NULL vengono utilizzati per riempire gli "spazi vuoti" nel set di risultati. Questa query corrisponde ai valori della colonna LISTID nella tabella LISTING (la tabella di sinistra) e SALES (la tabella di destra). I risultati mostrano che LISTIDs 2 e 3 non hanno portato ad alcuna vendita.

```
select listing.listid, sum(pricepaid) as price, sum(commission) as comm
from listing left outer join sales on sales.listid = listing.listid
where listing.listid between 1 and 5
group by 1
order by 1;

listid | price  |  comm
-------+--------+--------
     1 | 728.00 | 109.20
     2 | NULL   | NULL
     3 | NULL   | NULL
     4 |  76.00 |  11.40
     5 | 525.00 |  78.75
```

## DESTRA [ESTERNO]
<a name="right-outer-join"></a>

Restituisce tutti i valori dal riferimento alla tabella destra e i valori corrispondenti dal riferimento alla tabella sinistra oppure aggiunge NULL se non c'è corrispondenza. Viene anche chiamato *right* outer join.

Restituisce tutte le righe della tabella destra (seconda) e le righe corrispondenti della tabella sinistra (prima). Se non c'è alcuna corrispondenza nella tabella a sinistra, il set di risultati conterrà valori NULL per le colonne della tabella di sinistra. La parola chiave OUTER può essere omessa e il join può essere scritto semplicemente come RIGHT JOIN. L'opposto di un RIGHT OUTER JOIN è un LEFT OUTER JOIN, che restituisce tutte le righe della tabella di sinistra e le righe corrispondenti della tabella di destra.

**Sintassi:**

```
SELECT column1, column2, ..., columnn
FROM table1
RIGHT [OUTER] JOIN table2
ON table1.column = table2.column;
```

La seguente query restituirà tutte le righe della tabella clienti, insieme alle righe corrispondenti della tabella ordini. Se un cliente non ha ordini, il set di risultati includerà comunque le informazioni del cliente, con valori NULL per le colonne order\$1id e order\$1date.

```
SELECT orders.order_id, orders.order_date, customers.customer_id, customers.name
FROM orders
RIGHT OUTER JOIN customers
ON orders.customer_id = customers.customer_id;
```

La seguente query è un outer join. Questa query corrisponde ai valori della colonna LISTID nella tabella LISTING (la tabella di sinistra) e SALES (la tabella di destra). I risultati mostrano che LISTIDs 1, 4 e 5 corrispondono ai criteri.

```
select listing.listid, sum(pricepaid) as price, sum(commission) as comm
from listing right outer join sales on sales.listid = listing.listid
where listing.listid between 1 and 5
group by 1
order by 1;

listid | price  |  comm
-------+--------+--------
     1 | 728.00 | 109.20
     4 |  76.00 |  11.40
     5 | 525.00 |  78.75
```

## COMPLETO [ESTERNO]
<a name="full-join"></a>

Restituisce tutti i valori di entrambe le relazioni, aggiungendo valori NULL sul lato che non corrisponde. Viene anche chiamato join *esterno completo*. 

Restituisce tutte le righe delle tabelle sinistra e destra, indipendentemente dal fatto che esista una corrispondenza o meno. Se non c'è alcuna corrispondenza, il set di risultati conterrà valori NULL per le colonne della tabella che non hanno una riga corrispondente. La parola chiave OUTER può essere omessa e il join può essere scritto semplicemente come FULL JOIN. Il FULL OUTER JOIN è usato meno comunemente rispetto al LEFT OUTER JOIN o al RIGHT OUTER JOIN, ma può essere utile in alcuni scenari in cui è necessario visualizzare tutti i dati di entrambe le tabelle, anche se non ci sono corrispondenze.

**Sintassi:**

```
SELECT column1, column2, ..., columnn
FROM table1
FULL [OUTER] JOIN table2
ON table1.column = table2.column;
```

La seguente query restituirà tutte le righe delle tabelle clienti e ordini. Se un cliente non ha ordini, il set di risultati includerà comunque le informazioni del cliente, con valori NULL per le colonne order\$1id e order\$1date. Se a un ordine non è associato alcun cliente, il set di risultati includerà quell'ordine, con valori NULL per le colonne customer\$1id e name.

```
SELECT customers.customer_id, customers.name, orders.order_id, orders.order_date
FROM customers
FULL OUTER JOIN orders
ON customers.customer_id = orders.customer_id;
```

La seguente query è un fullr join. I full join mantengono i valori da una delle tabelle unite quando non viene trovata alcuna corrispondenza nell'altra tabella. Le tabelle sinistra e destra sono la prima e la seconda tabella elencate nella sintassi. I valori NULL vengono utilizzati per riempire gli "spazi vuoti" nel set di risultati. Questa query corrisponde ai valori della colonna LISTID nella tabella LISTING (la tabella di sinistra) e SALES (la tabella di destra). I risultati mostrano che LISTIDs 2 e 3 non hanno portato ad alcuna vendita.

```
select listing.listid, sum(pricepaid) as price, sum(commission) as comm
from listing full join sales on sales.listid = listing.listid
where listing.listid between 1 and 5
group by 1
order by 1;

listid | price  |  comm
-------+--------+--------
     1 | 728.00 | 109.20
     2 | NULL   | NULL
     3 | NULL   | NULL
     4 |  76.00 |  11.40
     5 | 525.00 |  78.75
```

La seguente query è un full join. Questa query corrisponde ai valori della colonna LISTID nella tabella LISTING (la tabella di sinistra) e SALES (la tabella di destra). Nei risultati vengono visualizzate solo le righe che non generano vendite (LISTIDs 2 e 3).

```
select listing.listid, sum(pricepaid) as price, sum(commission) as comm
from listing full join sales on sales.listid = listing.listid
where listing.listid between 1 and 5
and (listing.listid IS NULL or sales.listid IS NULL)
group by 1
order by 1;

listid | price  |  comm
-------+--------+--------
     2 | NULL   | NULL
     3 | NULL   | NULL
```

## [SINISTRA] SEMI
<a name="left-semi-join"></a>

Restituisce i valori dal lato sinistro del riferimento alla tabella che corrisponde a quello destro. Viene anche chiamato *left semi join*. 

Restituisce solo le righe della tabella sinistra (prima) che hanno una riga corrispondente nella tabella destra (seconda). Non restituisce alcuna colonna della tabella di destra, ma solo le colonne della tabella di sinistra. Il LEFT SEMI JOIN è utile quando si desidera trovare le righe di una tabella che hanno una corrispondenza in un'altra tabella, senza dover restituire alcun dato dalla seconda tabella. Il LEFT SEMI JOIN è un'alternativa più efficiente all'utilizzo di una sottoquery con una clausola IN o EXISTS.

**Sintassi:**

```
SELECT column1, column2, ..., columnn
FROM table1
LEFT SEMI JOIN table2
ON table1.column = table2.column;
```

La seguente query restituirà solo le colonne customer\$1id e name della tabella customers, per i clienti che hanno almeno un ordine nella tabella ordini. Il set di risultati non includerà alcuna colonna della tabella degli ordini.

```
SELECT customers.customer_id, customers.name
FROM customers
LEFT SEMI JOIN orders
ON customers.customer_id = orders.customer_id;
```

## CROSS JOIN
<a name="cross-join"></a>

Restituisce il prodotto cartesiano di due relazioni. Ciò significa che il set di risultati conterrà tutte le possibili combinazioni di righe delle due tabelle, senza applicare alcuna condizione o filtro.

Il CROSS JOIN è utile quando è necessario generare tutte le possibili combinazioni di dati da due tabelle, ad esempio nel caso di creazione di un report che mostri tutte le possibili combinazioni di informazioni sui clienti e sui prodotti. Il CROSS JOIN è diverso dagli altri tipi di join (INNER JOIN, LEFT JOIN, ecc.) perché non ha una condizione di join nella clausola ON. La condizione di unione non è richiesta per un CROSS JOIN.

**Sintassi:**

```
SELECT column1, column2, ..., columnn
FROM table1
CROSS JOIN table2;
```

La seguente query restituirà un set di risultati che contiene tutte le possibili combinazioni di customer\$1id, customer\$1name, product\$1id e product\$1name dalle tabelle clienti e prodotti. Se la tabella clienti ha 10 righe e la tabella prodotti ha 20 righe, il set di risultati di CROSS JOIN conterrà 10 x 20 = 200 righe.

```
SELECT customers.customer_id, customers.name, products.product_id, products.product_name
FROM customers
CROSS JOIN products;
```

La seguente query è un cross join o un join cartesiano della tabella LISTING e della tabella SALES con un predicato per limitare i risultati. Questa query corrisponde ai valori delle colonne LISTID nella tabella SALES e nella tabella LISTING per LISTIDs 1, 2, 3, 4 e 5 in entrambe le tabelle. I risultati mostrano che 20 righe soddisfano i criteri.

```
select sales.listid as sales_listid, listing.listid as listing_listid
from sales cross join listing
where sales.listid between 1 and 5
and listing.listid between 1 and 5
order by 1,2;

sales_listid | listing_listid
-------------+---------------
1            | 1
1            | 2
1            | 3
1            | 4
1            | 5
4            | 1
4            | 2
4            | 3
4            | 4
4            | 5
5            | 1
5            | 1
5            | 2
5            | 2
5            | 3
5            | 3
5            | 4
5            | 4
5            | 5
5            | 5
```

## ANTI JOIN
<a name="anti-join"></a>

Restituisce i valori del riferimento alla tabella sinistra che non corrispondono al riferimento alla tabella destra. Viene anche chiamato *antijoin sinistro*.

L'ANTI JOIN è un'operazione utile quando si desidera trovare le righe di una tabella che non hanno una corrispondenza in un'altra tabella. 

**Sintassi:**

```
SELECT column1, column2, ..., columnn
FROM table1
LEFT ANTI JOIN table2
ON table1.column = table2.column;
```

La seguente query restituirà tutti i clienti che non hanno effettuato ordini.

```
SELECT customers.customer_id, customers.name
FROM customers
LEFT ANTI JOIN orders
ON customers.customer_id = orders.customer_id
WHERE orders.order_id IS NULL;
```

## NATURAL
<a name="natural-join"></a>

Speciifica che le righe delle due relazioni verranno associate implicitamente in termini di uguaglianza per tutte le colonne con nomi corrispondenti. 

Abbina automaticamente le colonne con lo stesso nome e tipo di dati tra le due tabelle. Non richiede di specificare esplicitamente la condizione di unione nella clausola ON. Combina tutte le colonne corrispondenti tra le due tabelle nel set di risultati.

NATURAL JOIN è una comoda abbreviazione quando le tabelle che stai unendo hanno colonne con gli stessi nomi e tipi di dati. Tuttavia, in genere si consiglia di utilizzare il più esplicito INNER JOIN... Sintassi ON per rendere le condizioni di unione più esplicite e facili da capire.

**Sintassi:**

```
SELECT column1, column2, ..., columnn
FROM table1
NATURAL JOIN table2;
```

L'esempio seguente è un'unione naturale tra due tabelle `employees` e`departments`, con le seguenti colonne: 
+ `employees`tabella: `employee_id``first_name`,`last_name`, `department_id `
+ `departments`tavolo:`department_id`, `department_name `

La seguente query restituirà un set di risultati che include il nome, il cognome e il nome del reparto per tutte le righe corrispondenti tra le due tabelle, in base alla `department_id` colonna.

```
SELECT e.first_name, e.last_name, d.department_name
FROM employees e
NATURAL JOIN departments d;
```

Di seguito è riportato un esempio di join naturale tra due tabelle. In questo caso, le colonne listid, sellerid, eventid e dateid hanno nomi e tipi di dati identici in entrambe le tabelle e quindi vengono utilizzate come colonne di join. I risultati sono limitati a cinque righe.

```
select listid, sellerid, eventid, dateid, numtickets
from listing natural join sales
order by 1
limit 5;

listid | sellerid  | eventid | dateid | numtickets
-------+-----------+---------+--------+-----------
113    | 29704     | 4699    | 2075   | 22
115    | 39115     | 3513    | 2062   | 14
116    | 43314     | 8675    | 1910   | 28
118    | 6079      | 1611    | 1862   | 9
163    | 24880     | 8253    | 1888   | 14
```