Allereerst, om volledig gelijkwaardig te zijn, had de eerste vraag moeten zijn geschreven
SELECT mw.*,
nvs.*
FROM mst_words mw
LEFT JOIN (SELECT *
FROM vocab_stats
WHERE owner = 1111) AS nvs ON mw.no = nvs.vocab_no
WHERE (nvs.correct > 0 )
AND mw.level = 1
Zodat mw.* en nvs.* samen dezelfde set produceren als de singuliere * van de 2e query. De query zoals je hebt geschreven kan een INNER JOIN gebruiken, omdat deze een filter bevat op nvs.correct.
Het algemene formulier
TABLEA LEFT JOIN TABLEB ON <CONDITION>
attempts
om TableB-records te vinden op basis van de voorwaarde. Als het mislukt, worden de resultaten van TABLEA bewaard, waarbij alle kolommen van TableB zijn ingesteld op NULL. In tegenstelling
TABLEA INNER JOIN TABLEB ON <CONDITION>
ook attempts
om TableB-records te vinden op basis van de voorwaarde. Echter , als het niet lukt, wordt het specifieke record uit TabelA verwijderd uit de uitvoerresultatenset.
De ANSI-standaard voor CROSS JOIN produceert een Cartesiaans product tussen de twee tafels.
TABLEA CROSS JOIN TABLEB
-- # or in older syntax, simply using commas
TABLEA, TABLEB
De bedoeling van de syntaxis is dat ELKE rij in TABLEA wordt samengevoegd met ELKE rij in TABLEB. Dus 4 rijen in A en 3 rijen in B produceren 12 rijen output. In combinatie met voorwaarden in de WHERE-component, produceert het soms hetzelfde gedrag van de INNER JOIN, omdat ze hetzelfde uitdrukken (voorwaarde tussen A en B => behouden of niet). Bij het lezen is het echter een stuk duidelijker wat de bedoeling is als je INNER JOIN gebruikt in plaats van komma's.
Wat de prestaties betreft, verwerken de meeste DBMS een LEFT-join sneller dan een INNER JOIN. De kommanotatie kan ertoe leiden dat databasesystemen de bedoeling verkeerd interpreteren en een slecht queryplan produceren - dus nog een pluspunt voor SQL92-notatie.
Waarom hebben we LEFT JOIN nodig? Als de uitleg van LEFT JOIN hierboven nog steeds niet genoeg is (houd records in A zonder overeenkomsten in B), bedenk dan dat om hetzelfde te bereiken, je een complexe UNION nodig hebt tussen twee sets met de oude kommanotatie om hetzelfde effect te bereiken . Maar zoals eerder vermeld , dit is niet van toepassing op jouw voorbeeld, dat is eigenlijk een INNER JOIN die zich verschuilt achter een LEFT JOIN.
Opmerkingen:
- De RIGHT JOIN is hetzelfde als LEFT, behalve dat deze begint met TABLEB (rechterkant) in plaats van A.
- RIGHT en LEFT JOINS zijn beide OUTER joins. Het woord OUTER is optioneel, d.w.z. het kan worden geschreven als
LEFT OUTER JOIN
. - Het derde type OUTER-join is FULL OUTER-join, maar dat wordt hier niet besproken.