次のようなものがあるとします。
CURSOR foo_cur IS
SELECT * FROM foo;
...
DELETE FROM foo WHERE bar=1;
FOR row IN foo_cur
LOOP
...
END LOOP;
foo
カーソルを開く前に行を削除した場合、これらの行は引き続きカーソル結果の一部になりますか? クエリSELECT * FROM foo
は行で実行されますFOR row IN foo_cur
か?
次のようなものがあるとします。
CURSOR foo_cur IS
SELECT * FROM foo;
...
DELETE FROM foo WHERE bar=1;
FOR row IN foo_cur
LOOP
...
END LOOP;
foo
カーソルを開く前に行を削除した場合、これらの行は引き続きカーソル結果の一部になりますか? クエリSELECT * FROM foo
は行で実行されますFOR row IN foo_cur
か?
カーソルから返される行のセットは、カーソルが開かれた時点で決定されます (ループOPEN
によって明示的または暗黙的に)。FOR
この場合、削除した行はループに返されません。
通常、クエリは一度にすべて実行されるわけではありません。Oracle は、次の行セットをフェッチするのに十分なクエリを実行し、それらの行を PL/SQL VM に返し、さらに行をフェッチする要求が来るまで待機します。11g では、Oracle はBULK COLLECT
一度に 100 行の暗黙的な処理を行うため、ループの 100 回の反復ごとに、返される行がなくなるまでクエリがさらに実行されます。マルチバージョン読み取りの一貫性により、Oracle は、コードの実行中に他のセッションが変更を行ってコミットしている場合でも、カーソルが開かれたときに存在していたデータを常に返します。