语法:事务
SELECT ... FOR UPDATE [OF column_list][WAIT n|NOWAIT][SKIP LOCKED];ip
其中OF 子句用于指定即将更新的列,即锁定行上的特定列; WAIT 子句指定等待其余用户释放锁的秒数,防止无限期的等待。资源
使用“FOR UPDATE WAIT”子句的优势以下:it
1防止无限期地等待被锁定的行;table
2容许应用程序中对锁的等待时间进行更多的控制。date
3对于交互式应用程序很是有用,由于这些用户不能等待不肯定select
4若使用了skip locked,则能够越过锁定的行,不会报告由wait n引起的‘资源忙’异常报告语法
实验:程序
create table t(a varchar2(20),b varchar2(20));im
insert into t values('1','1');
insert into t values('2','2');
insert into t values('3','3');
insert into t values('4','4');
insert into t values('5','5');
insert into t values('6','6');
(1)在PLSQL Developer中打开两个窗口,在窗口1中执行
select * from t where a='1' for update;
结果以下
在窗口2中执行
select * from t where a='1';
结果以下
可见此时能正常查询。
在窗口2中执行
select * from t where a='1' for update;
发现没法查询出结果且PLSQL Developer的执行按钮一直为灰色。
这是由于表被窗口1里的语句锁住了,窗口2处于等待状态。
只有等窗口1中提交了事务以后才能在窗口2中正常执行上述语句。
在窗口1中点击提交事务的按钮后,窗口2中立马显示出正常结果
把窗口1和2中未提交的事务都提交,以便进行下一步的实验。
(2)
在窗口1中执行select * from t where a='1' for update;
在窗口2中执行select * from t where a='1' for update nowait;
立马报资源正忙的错误:
关掉上面的错误提示窗口,在窗口2中执行
select * from t where a='1' for update wait 6;
则6秒以后报错:
关掉上面的错误提示,在窗口2中执行
select * from t where a='1' for update skip locked;
则既不等待,也不报错,也查询不出结果:
把窗口1和2中未提交的事务都提交,以便进行下一步的实验。
(3)
在窗口1中执行:
select * from t where rownum<=3 for update skip locked;
结果以下:
在窗口2中执行:
select * from t where rownum<=6 for update skip locked;
结果以下:
可见前三条数据因被窗口1锁住而没有查出来。