ORACLE 约束延迟验证的特性deferred的作用与场景?
之前约束这一块都由开发那边管,今天接手约束,突然有一个疑问?约束deferred延迟验证的作用是什么?适合于什么应用场景?因为基于事务的特性,任何一个事务要么成功,要么失败,即使你整个事务前面999万条insert记录都不违反约束,但是如果第一千万条insert记录违反了约束,那么基于这个错误会回滚整个事务。既然如此为什么oracle要引出约束的延迟验证这一个属性?这不是白白浪费了执行insert 999万条记录所产生的资源损耗吗?这样还不如执行启用约束立即验证,反而能提前结束事务,释放系统资源。那么deferred还有什么神秘的面纱吗? SQL> create table p ( pk int primary key );Table created.
SQL> create table c( t1 int,fk int constraint c_fk references p(pk) deferrable initially immediate);
Table created.
SQL> insert into p values ( 1 );
1 row created.
SQL> insert into p values ( 3 );
1 row created.
SQL> insert into c values ( 2,1 );
1 row created.
SQL> commit;
Commit complete.
SQL> select * from p;
PK
----------
1
3
SQL> select * from c;
T1 FK
---------- ----------
2 1
此时若你想将 P 和 C表中的PK=1 FK=1 都更新为PK=2 FK=2 如何做呢?
SQL> update p set pk=2 where pk=1;
update p set pk=2 where pk=1
*
ERROR at line 1:
ORA-02292: integrity constraint (SYS.C_FK) violated - child record found
SQL> update c set fk=2 where fk=1;
update c set fk=2 where fk=1
*
ERROR at line 1:
ORA-02291: integrity constraint (SYS.C_FK) violated - parent key not found
你单独更新 P 和 C 表都不可以, 要么你删除数据后 重新插入
要么:
set constraint c_fk deferred;
SQL> set constraint c_fk deferred;
Constraint set.
SQL> update p set pk=2 where pk=1;
1 row updated.
SQL> update c set fk=2 where fk=1;
1 row updated.
SQL> commit;
Commit complete.
SQL> select * from p;
PK
----------
2
3
SQL> select * from c;
T1 FK
---------- ----------
2 2
这样够清楚了吗? 没想过这种场景!原来还有这种用法,我就说这deferred的作用是啥!秒懂!感谢,刘大
页:
[1]