有关上下文,请参阅 Vlad 的答案,我只是在 Oracle 中添加等价物,因为有一些“陷阱”需要注意。
这
SELECT * FROM t order by x limit 2 FOR UPDATE OF t SKIP LOCKED
不会以您可能期望的方式直接转换为 Oracle。如果我们看一些翻译选项,我们可能会尝试以下任何一种:
SQL> create table t as
2 select rownum x
3 from dual
4 connect by level <= 100;
Table created.
SQL> declare
2 rc sys_refcursor;
3 begin
4 open rc for select * from t order by x for update skip locked fetch first 2 rows only;
5 end;
6 /
open rc for select * from t order by x for update skip locked fetch first 2 rows only;
*
ERROR at line 4:
ORA-06550: line 4, column 65:
PL/SQL: ORA-00933: SQL command not properly ended
ORA-06550: line 4, column 15:
PL/SQL: SQL Statement ignored
SQL> declare
2 rc sys_refcursor;
3 begin
4 open rc for select * from t order by x fetch first 2 rows only for update skip locked ;
5 end;
6 /
declare
*
ERROR at line 1:
ORA-02014: cannot select FOR UPDATE from view with DISTINCT, GROUP BY, etc.
ORA-06512: at line 4
或者尝试回退到 ROWNUM 选项
SQL> declare
2 rc sys_refcursor;
3 begin
4 open rc for select * from ( select * from t order by x ) where rownum <= 10 for update skip locked;
5 end;
6 /
declare
*
ERROR at line 1:
ORA-02014: cannot select FOR UPDATE from view with DISTINCT, GROUP BY, etc.
ORA-06512: at line 4
你不会得到任何快乐。因此,您需要自己控制“n”行的获取。因此,您可以编写如下代码:
SQL> declare
2 rc sys_refcursor;
3 res1 sys.odcinumberlist := sys.odcinumberlist();
4 begin
5 open rc for select * from t order by x for update skip locked;
6 fetch rc bulk collect into res1 limit 10;
7 end;
8 /
PL/SQL procedure successfully completed.