Från Oracle-dokumentationen :
Om din fråga refererar till en enskild tabell är det ingen skillnad mellan FOR UPDATE och FOR UPDATE OF ... , men den senare kan fortfarande vara användbar som självdokumentation för att indikera vilka kolumner du tänker uppdatera. Det begränsar dock inte vad du kan uppdatera. Om du har:
CURSOR cur IS SELECT * FROM emp FOR UPDATE OF sal;
då kan du fortfarande göra:
UPDATE emp SET comm = comm * 1.1 WHERE CURRENT OF cur;
Men om det finns mer än en tabell så FOR UPDATE OF ... kommer endast att låsa raderna i tabellerna som innehåller kolumnerna du anger i OF klausul.
Tvärtemot vad jag tror att du säger i frågan. anger FOR UPDATE OF sal låser inte bara sal kolumn; du kan aldrig låsa en enda kolumn, det lägsta låset är på radnivå. (Läs mer om lås
). Den låser alla rader i tabellen som innehåller SAL kolumn, som väljs av frågan.
I uppdateringen av din fråga ansluter din markörfråga till emp och dept , men OF klausulen har bara sal , en kolumn i emp tabell. Raderna i emp tabell kommer att låsas när markören öppnas, och dessa lås kommer inte att släppas förrän du commit eller rollback den sessionen. Inom markörslingan kan du göra:
UPDATE emp SET ... WHERE CURRENT OF emp_cur;
... för att uppdatera raden i emp tabell som relaterar till denna iteration av slingan. Du kan inte gör:
UPDATE dept SET ... WHERE CURRENT OF emp_cur;
... eftersom rader i dept Tabellen är inte låst eftersom inga kolumner fanns i OF . Det betyder också att dept i din andra session rader kan uppdateras fritt, eftersom de inte är låsta av den första sessionen.