Συνενώσεις (joins)

Επιλογή δεδομένων από δύο ή περισσότερους πίνακες

Έστω οι δύο παρακάτω πίνακες table_a και table_b

table_atable_b
A_IDA1A2W
1125
2426
3233
4141
B_IDB1B2W
1522
2315
3131
4457

Το ερώτημα:

SELECT * 
FROM table_a, table_b;

Επιλέγει όλους τους πιθανούς συνδυασμούς, δηλαδή 4*4=16 πλειάδες όπως φαίνονται στον παρακάτω πίνακα (δεν διαγράφονται πιθανές διπλοεγγραφές).

Το παραπάνω ερώτημα αντιστοιχεί στο καρτεσιανό γινόμενο (table_a X table_b)

A_IDA1A2WB_IDB1B2W
11251522
24261522
32331522
41411522
11252315
24262315
32332 315
4 1 4 1 2 3 1 5
1 1 2 5 3 1 3 1
2 4 2 6 3 1 3 1
3 2 3 3 3 1 3 1
4 1 4 1 3 1 3 1
1 1 2 5 4 4 5 7
2 4 2 6 4 4 5 7
3 2 3 3 4 4 5 7
4 1 4 1 4 4 5 7

Μπορείτε να έχετε περισσότερους από δύο πίνακες όπως:

SELECT * 
FROM table_a, table_b, table_c;

Συνένωση Θ (θήτα)

Αν προσθέσουμε το WHERE στο παραπάνω ερώτημα θα έχουμε μια συνένωση Θ (θήτα).

SELECT * 
FROM table_a, table_b 
WHERE a1>b1;
A_IDA1A2WB_IDB1B2W
2 4 2 6 2 3 1 5
2 4 2 6 3 1 3 1
3 2 3 3 3 1 3 1

Στην περίπτωση που τα πεδία που συγκρίνουμε έχουν ίδιο όνομα τα ξεχωρίζουμε βάζοντας το όνομα του πίνακα και μια τελεία όπως στο παρακάτω παράδειγμα.

SELECT * 
FROM table_a, table_b 
WHERE  table_a.w > table_b.w;
A_IDA1A2WB_IDB1B2W
1 1 2 5 1 5 2 2
2 4 2 6 1 5 2 2
3 2 3 3 1 5 2 2
2 4 2 6 2 3 1 5
1 1 2 5 3 1 3 1
2 4 2 6 3 1 3 1
3 2 3 3 3 1 3 1

Συνένωση Ισότητας (equijoin)

Αν προσθέσουμε στο WHERE συνθήκη ισότητας έχουμε συνένωση ισότητας.

SELECT * 
FROM table_a, table_b 
WHERE a2=b2;
A_IDA1A2WB_IDB1B2W
1 1 2 5 1 5 2 2
2 4 2 6 1 5 2 2
3 2 3 3 3 1 3 1

Επίσης όταν έχουμε ίδια ονόματα πεδίων σε δύο πίνακες, τότε έχουμε:

SELECT * 
FROM table_a, table_b 
WHERE table_a.w=table_b.w;

Συνενώσεις joins

Οι συνενώσεις (joins) χρησιμοποιούνται για ερωτήματα σε δύο οι περισσότερους πίνακες για τους οποίους υπάρχει κάποια σχέση ανάμεσα στα γνωρίσματα (συνήθως ανάμεσα στα κλειδιά).

JOIN ή INNER JOIN

Η JOIN είναι αντίστοιχη του καρτεσιανού γινομένου.

SELECT * 
FROM table_a JOIN table_b;
A_IDA1A2WB_IDB1B2W
1 1 2 5 1 5 2 2
2 4 2 6 1 5 2 2
3 2 3 3 1 5 2 2
4 1 4 1 1 5 2 2
1 1 2 5 2 3 1 5
2 4 2 6 2 3 1 5
3 2 3 3 2 3 1 5
4 1 4 1 2 3 1 5
1 1 2 5 3 1 3 1
2 4 2 6 3 1 3 1
3 2 3 3 3 1 3 1
4 1 4 1 3 1 3 1
1 1 2 5 4 4 5 7
2 4 2 6 4 4 5 7
3 2 3 3 4 4 5 7
4 1 4 1 4 4 5 7

Μπορείτε να κάνετε JOIN περισσότερους από δύο πίνακες όπως:

SELECT * 
FROM table_a JOIN table_b JOIN table_c;

Με την JOIN μπορείτε επίσης να χρησιμοποιείτε και το WHERE

SELECT * 
FROM table_a JOIN table_b 
where a1=b1;

Η άλλη επιλογή είναι η αντικατάσταση του WHERE με το ON ή το USING που χρησιμοποιούνται στις συνενώσεις δύο πινάκων.

    • ON χρησιμοποιείται για συνένωση στηλών με διαφορετικό όνομα
SELECT *
FROM table_a JOIN table_b
ON  table_a.a1 =  table_b.b1;
A_IDA1A2WB_IDB1B2W
1 1 2 5 3 1 3 1
4 1 4 1 3 1 3 1
2 4 2 6 4 4 5 7
    • USING χρησιμοποιείται για συνένωση στηλών με ίδιο όνομα (έστω η στήλη w). Επίσης, με τον τελεστή USING επιλέγονται μόνο οι εγγραφές για τις οποίες οι αντίστοιχες τιμές στο πεδίο ή πεδία με ίδιο όνομα (w) είναι ίσες. Τέλος, επιστρέφεται μόνο η μία στήλη ή στήλες με το κοινό όνομα.
SELECT *
FROM table_a JOIN table_b
USING (w);
WA_IDA1A2B_IDB1B2
5 1 1 2 2 3 1
1 4 1 4 3 1 3

NATURAL JOIN

Η NATURAL JOIN λειτουργεί όπως η JOIN σε συνδυασμό με το USING. Η διαφορά είναι ότι δεν χρειάζεται το USING. Η NATURAL JOIN ψάχνει όλα τα πεδία με κοινό όνομα και εφαρμόζει το USING χωρίς να χρειάζεται να δηλωθεί.

SELECT * 
FROM table_a NATURAL JOIN table_b;
WA_IDA1A2B_IDB1B2
5 1 1 2 2 3 1
1 4 1 4 3 1 3

Ή για περισσότερους πίνακες.

SELECT * 
FROM table_a NATURAL JOIN table_b NATURAL JOIN table_c;

Στην επιλογή με NATURAL JOIN μπορεί να ακολουθεί και η WHERE μετά την FROM.

SELECT *
FROM table_a NATURAL JOIN table_b
WHERE a1 = b1;
WA_IDA1A2B_IDB1B2
1 4 1 4 3 1 3

OUTER JOINS

Σε μια συνένωση τύπου OUTER JOIN δεν είναι υποχρεωτικό να επιστρέφονται μόνο οι εγγραφές που υπακούουν στη συνθήκη, αλλά και όλες οι εγγραφές από τον έναν ή και από τους δύο πίνακες της συνένωσης.

Έτσι έχουμε:

  • LEFT OUTER JOIN ή LEFT JOIN
  • RIGHT OUTER JOIN ή RIGHT JOIN
  • FULL OUTER JOIN ή FULL JOIN

Για τις OUTER συνενώσεις δεν υπάρχει αντίστοιχη εντολή στην πρότυπη SQL

LEFT JOIN

Η LEFT JOIN επιστρέφει όλες τις εγγραφές από τον αριστερό πίνακα και κρατάει από τον δεξιό αυτές που ικανοποιούν τη συνθήκη. Στα κενά κελιά μπαίνει το NULL.

SELECT * 
FROM table_a LEFT JOIN table_b 
ON a1 = b1;
A_IDA1A2WB_IDB1B2W
1 1 2 5 3 1 3 1
2 4 2 6 4 4 5 7
3 2 3 3 NULL NULL NULL NULL
4 1 4 1 3 1 3 1

Επίσης με τη USING.

SELECT * 
FROM table_a LEFT JOIN table_b 
USING(w);
WA_IDA1A2B_IDB1B2
5 1 1 2 2 3 1
6 2 4 2 NULL NULL NULL
3 3 2 3 NULL NULL NULL
1 4 1 4 3 1 3

Εναλλακτικά με NATURAL LEFT JOIN

SELECT *
FROM table_a NATURAL LEFT JOIN table_b;
WA_IDA1A2B_IDB1B2
5 1 1 2 2 3 1
6 2 4 2 NULL NULL NULL
3 3 2 3 NULL NULL NULL
1 4 1 4 3 1 3

RIGHT JOIN

Η RIGHT JOIN επιστρέφει όλες τις εγγραφές από τον δεξιό πίνακα και κρατάει από τον αριστερό αυτές που ικανοποιούν τη συνθήκη. Στα κενά κελιά μπαίνει το NULL.

SELECT * 
FROM table_a RIGHT JOIN table_b 
ON a1 = b1;
A_IDA1A2WB_IDB1B2W
NULL NULL NULL NULL 1 5 2 2
NULL NULL NULL NULL 2 3 1 5
1 1 2 5 3 1 3 1
4 1 4 1 3 1 3 1
2 4 2 6 4 4 5 7

Επίσης με τη USING.

SELECT * 
FROM table_a RIGHT JOIN table_b 
USING(W);
WB_IDB1B2A_IDA1A2
2 1 5 2 NULL NULL NULL
5 2 3 1 1 1 2
1 3 1 3 4 1 4
7 4 4 5 NULL NULL NULL

Εναλλακτικά με NATURAL RIGHT JOIN

SELECT * 
FROM table_a NATURAL RIGHT JOIN table_b;
WB_IDB1B2A_IDA1A2
2 1 5 2 NULL NULL NULL
5 2 3 1 1 1 2
1 3 1 3 4 1 4
7 4 4 5 NULL NULL NULL

FULL JOIN

Η FULL JOIN είναι ένας συνδυασμός των δύο παραπάνω (LEFT JOIN και RIGHT JOIN) και επιστρέφει όλες τις εγγραφές που ικανοποιούν τη συνθήκη. Στα κενά κελιά μπαίνει το NULL.

SELECT * 
FROM table_a FULL JOIN table_b 
ON a1 = b1;

Επειδή η MySQL δεν υποστηρίζει την FULL JOIN μπορούμε να χρησιμοποιήσουμε την παρακάτω ισοδύναμη έκφραση:

SELECT *
FROM table_a LEFT JOIN table_b 
ON a1 = b1

UNION

SELECT *
FROM table_a RIGHT JOIN table_b 
ON a1 = b1;
A_IDA1A2WB_IDB1B2W
1 1 2 5 3 1 3 1
2 4 2 6 4 4 5 7
3 2 3 3 NULL NULL NULL NULL
4 1 4 1 3 1 3 1
NULL NULL NULL NULL 1 5 2 2
NULL NULL NULL NULL 2 3 1 5

Επίσης για την παρακάτω έκφραση

SELECT * 
FROM table_a FULL JOIN table_b 
USING(W);

μπορούμε να χρησιμοποιήσουμε την ισοδύναμη

SELECT *
FROM table_a LEFT JOIN table_b 
USING(w)

UNION

SELECT *
FROM table_a RIGHT JOIN table_b 
USING(w);
WA_IDA1A2B_IDB1B2
5 1 1 2 2 3 1
6 2 4 2 NULL NULL NULL
3 3 2 3 NULL NULL NULL
1 4 1 4 3 1 3
2 1 5 2 NULL NULL NULL
5 2 3 1 1 1 2
1 3 1 3 4 1 4
7 4 4 5 NULL NULL NULL