oracle2个字段指定一个范围如何控制不能有重复或交叉
由于业务需要,表中tab1需要以下2个字段的值:
行号 startid endid
1 1 1
2 3 4
3 5 8
若插入: 2 2 允许
若插入: 9 12允许
若插入: 2 3 禁止
若插入: 6 7 禁止
若修改第2行为: 2 3 允许
若修改第2行为: 2 5 禁止
也就是说所有行的数值不能有重复或交叉!!!
现在需要在后台控制,我能想到的解决方案就是写了一个触发器,编译通过,插入错误的情况可以避免,但更新错误时触发器报ora-04091错误:
create or replace trigger t_tab1_idcheck before insert or update
on tab1 for each row
declare
ll_have number;
old_rowid varchar2(128);
new_startid number;
new_endid number;
begin
if inserting then
select count(*)
into ll_have
from tab1
where startid <= :new.endid
and endif >= :new.startid;--执行成功
if (ll_have > 0) then
raise_application_error(-20010,'error');
end if;
end if;
if updating then
new_rowid := :old.rowid;
new_startid := :new.startid;
new_endid := :new.endid;
select count(*)
into ll_have
from tab1
where startid <= new_endid
and endid >= new_startid
and rowid <> old_rowid;--执行报错
if (ll_have > 0) then
raise_application_error(-20010, 'error');
end if;
end if;
end;
请各位大侠帮我看看如何解决这个问题!或者有别的机制可以限制
这个过程是我按照题目的例子改的,没完全改好,其中new_rowid := :old.rowid应该是old_rowid := :old.rowid;
这句话的意思就是将本次更新的当前记录的最新值与除当前记录外的记录进行比较是否有交叉。
但是执行 old_rowid := :old.rowid;
new_startid := :new.startid;
new_endid := :new.endid;
select count(*)
into ll_have
from tab1
where startid <= new_endid
and endid >= new_startid
and rowid <> old_rowid;--执行报错ora-04091
-- 得用带“自治事务”的触发器,代码如下: create table tab1(r_id number, startid number, endid number); create or replace trigger t_tab1_idcheck before insert or updateon tab1 for each row declare PRAGMA AUTONOMOUS_TRANSACTION; ll_have number; begin if inserting then select count(1) into ll_have from tab1 where startid <= :new.endid and endid >= :new.startid; --执行成功 if (ll_have > 0) then raise_application_error(-20010,'error'); end if; end if; if updating then select count(*) into ll_have from tab1 where startid <= :new.endid and endid >= :new.startid and rowid <> :old.rowid; --执行报错 if (ll_have > 0) then raise_application_error(-20010, 'error'); end if; end if; end; / insert into tab1(r_id,startid,endid) values(1,1,1); insert into tab1(r_id,startid,endid) values(2,3,4); insert into tab1(r_id,startid,endid) values(3,5,8); commit; insert into tab1(r_id,startid,endid) values(4,2,2); commit; insert into tab1(r_id,startid,endid) values(5,9,12); commit; insert into tab1(r_id,startid,endid) values(6,2,3); commit; insert into tab1(r_id,startid,endid) values(7,6,7); commit;