在Oracle第三列中的值条件下,对2列的唯一约束

55ooxyrt  于 2023-11-17  发布在  Oracle
关注(0)|答案(2)|浏览(142)

我需要两列(X和Y)的值的组合是唯一的,但只有当第三列('STATUS')具有特定值时。如果第三列具有与前两列不同的值,则允许重复。
所有3列都不可为空。
我试过了,但没有用:

CREATE UNIQUE INDEX MY_UK ON MY_TABLE(X, Y, (CASE WHEN STATUS = 'ACTIVE' THEN STATUS ELSE NULL END));

字符串
它抱怨重复的值肯定不存在于STATUS = 'ACTIVE'的记录中,我猜是'NOT_ACTIVE' STATUS或其他什么冲突。有人知道解决方案吗?

du7egjpx

du7egjpx1#

像这样的,也许?
样品表:

SQL> -- status = ACTIVE    : X and Y have to be unique
SQL> --          NOT_ACTIVE: X and Y don't have to be unique
SQL> create table test (x, y, status) as
  2    select 1, 1, 'NOT_ACTIVE' from dual union all
  3    select 2, 3, 'ACTIVE'     from dual;

Table created.

字符串
Index * 将 * xy用一个在这两列中都不存在的字符连接起来。为什么?这样我们就可以避免误报;例如,12||3等于1||23,我们想避免这种情况:

SQL> create unique index ui1_test on test
  2    (case when status = 'ACTIVE' then x ||'-'|| y
  3          else null
  4     end);

Index created.


测试:
该行尚不存在,因此应该允许:

SQL> insert into test (x, y, status) values (5, 6, 'ACTIVE');

1 row created.


这一个也是一样-不存在,可以插入:

SQL> insert into test (x, y, status) values (1, 1, 'NOT_ACTIVE');

1 row created.


这样的行已经存在,因此您无法插入它:

SQL> insert into test (x, y, status) values (2, 3, 'ACTIVE');
insert into test (x, y, status) values (2, 3, 'ACTIVE')
*
ERROR at line 1:
ORA-00001: unique constraint (SCOTT.UI1_TEST) violated


值类似于前一个插入(xy存在于表中,但状态现在已更改,因此可以插入行):

SQL> insert into test (x, y, status) values (2, 3, 'NOT_ACTIVE');

1 row created.

SQL>

gc0ot86w

gc0ot86w2#

2个选项(一个基于@Littlefoot的答案):
唯一索引:

CREATE UNIQUE INDEX MY_UK_IX ON MY_TABLE (CASE "STATUS" WHEN 'V' THEN NULL ELSE TO_CHAR("X")||'^'||TO_CHAR("Y") END);

字符串
具有正常唯一约束的虚拟列:

ALTER TABLE MY_TABLE ADD (X_Y_UK VARCHAR2(100) GENERATED ALWAYS AS (CASE WHEN STATUS = 'V' THEN NULL ELSE (X||'^'||Y) END))
ALTER TABLE MY_TABLE ADD CONSTRAINT CHECK_X_Y_UK UNIQUE (X_Y_UK)

相关问题