Uw UPDATE
zoekopdracht zou er als volgt uit moeten zien:
UPDATE table2 t2
SET val2 = t1.val1
FROM table1 t1
WHERE t2.table2_id = t1.table2_id
AND t2.val2 IS DISTINCT FROM t1.val1; -- optional, see below
Zoals u het had, was er geen koppeling tussen de afzonderlijke rijen van de twee tabellen. Elke rij zou worden opgehaald uit table1
voor elke rij in table2
. Dit sloeg nergens op (op een dure manier) en veroorzaakte ook de syntaxisfout, omdat een subquery-expressie op deze plaats slechts één enkele waarde mag retourneren.
Ik heb dit opgelost door de twee tabellen samen te voegen op table2_id
. Vervang dat door wat de twee werkelijk met elkaar verbindt.
Ik herschreef de UPDATE
om mee te doen aan table1
(met de FROM
clausule) in plaats van gecorreleerde subquery's uit te voeren, omdat dat doorgaans een orde van grootte sneller is.
Het voorkomt ook dat table2.val2
zou teniet worden gedaan als er geen overeenkomende rij wordt gevonden in table1
. In plaats daarvan niets gebeurt er met dergelijke rijen met deze vorm van de zoekopdracht.
U kunt tabeluitdrukkingen toevoegen aan de FROM
lijst zoals zou in een gewone SELECT
(tabellen, subquery's, set-retourfuncties, ...). De handleiding:
from_list
Een lijst met tabeluitdrukkingen, waardoor kolommen uit andere tabellen kunnen verschijnen in de
WHERE
voorwaarde en de update-expressies. Dit is vergelijkbaar met de lijst met tabellen die gespecificeerd kunnen worden in deFROM
Clausule van eenSELECT
uitspraak. Merk op dat de doeltabel niet mag voorkomen in defrom_list
, tenzij u een self-join van plan bent (in dat geval moet het verschijnen met een alias in defrom_list
).
De laatste WHERE
clausule voorkomt updates die niets zouden veranderen - wat praktisch altijd een goed idee is (bijna volledige kosten maar geen winst, exotische uitzonderingen zijn van toepassing). Als zowel de oude als de nieuwe waarde gegarandeerd NOT NULL
zijn , vereenvoudigen tot:
AND t2.val2 <> t1.val1
- Hoe kan (of kan ik) DISTINCT SELECTEREN op meerdere kolommen?