约束状态
1.1. 约束状态
约束条件有如下的选项,且有如下图标的组合
|
是否验证 |
Validate |
Novalidate |
||
|
已有记录 |
新增/删除记录 |
已有记录 |
新增/删除记录 |
|
|
Enable |
Yes |
Yes |
No |
Yes |
|
Disable |
Yes |
No |
No |
No |
1.1.1. ENABLED&VALIDATED(默认)
Enable/disable是针对表内已有数据进行约束;Validate/disvalidate是针对新增加到表的数据进行约束;
1)建表,写入初始数据 0 (默认为 ENABLED &VALIDATED)
SQL> create table t(a int,b int,c int,d int);
Table created.
SQL> insert into t values(0,0,0,0);
1 row created.
SQL> commit;
Commit complete.
SQL> select * from t;
A B C D
---------- ---------- ---------- ----------
0 0 0 0
2)增加 check,约束条件为 a>0,创建失败。因为表中 a 的数据不符合条件,报错说明,在创建的同时对已存在的数据进行了验证
SQL> alter table t add constraint ck_t check (a>0);
alter table t add constraint ck_t check (a>0)
*
ERROR at line 1:
ORA-02293: cannot validate (SCOTT.CK_T) - check constraint violated
3)增加 check,约束条件为 a>=0,表中数据符合条件,创建成功
SQL> alter table t add constraint ck_t check(a>=0);
Table altered.
4)A 字段插入不符合 check 的数据,报错,说明约束对新插入的数据也起作用
SQL> insert into t(a) values(-1);
insert into t(a) values(-1)
*
ERROR at line 1:
ORA-02290: check constraint (SCOTT.CK_T) violated
5)查看一下约束条件状态(默认为 ENABLED &VALIDATED)
SQL> desc user_constraints
Name Null? Type
----------------------------------------- --------
OWNER VARCHAR2(30)
CONSTRAINT_NAME NOT NULL VARCHAR2(30)
CONSTRAINT_TYPE VARCHAR2(1)
TABLE_NAME NOT NULL VARCHAR2(30)
SEARCH_CONDITION LONG
R_OWNER VARCHAR2(30)
R_CONSTRAINT_NAME VARCHAR2(30)
DELETE_RULE VARCHAR2(9)
STATUS VARCHAR2(8)
DEFERRABLE VARCHAR2(14)
DEFERRED VARCHAR2(9)
VALIDATED VARCHAR2(13)
GENERATED VARCHAR2(14)
BAD VARCHAR2(3)
RELY VARCHAR2(4)
LAST_CHANGE DATE
INDEX_OWNER VARCHAR2(30)
INDEX_NAME VARCHAR2(30)
INVALID VARCHAR2(7)
VIEW_RELATED VARCHAR2(14)
SQL> select CONSTRAINT_NAME,STATUS,VALIDATED,SEARCH_CONDITION from user_constraints where table_name=upper('t');
CONSTRAINT_NAME STATUS VALIDATED SEARCH_CONDITION
-------------------- -------- ------------- --------------------
CK_T ENABLED VALIDATED a>=0
1.1.2. ENABLE&NOVALIDATE
6)
b 字段创建 check 约束,条件为 b>0,表中 b 字段已存在数据 0,不符合 check 条件,
不过,由于验证字段为 novalidate,状态为 enable,所以,原有的数据不进行验证,新增数据验证
SQL> select * from t;
A B C D
---------- ---------- ---------- ----------
0 0 0 0
SQL> alter table t add constraint ck_t_b check(b>0) enable
2 novalidate;(针对现有字段数据的约束)
Table altered.
SQL> insert into t(b) values (-1);
insert into t(b) values (-1)
*
ERROR at line 1:
ORA-02290: check constraint (SCOTT.CK_T_B) violated
SQL> select constraint_name,status,validated,search_condition
2 from user_constraints where table_name='T';
CONSTRAINT_NAME STATUS VALIDATED SEARCH_CONDITION
-------------------- -------- ------------- --------------------
CK_T ENABLED VALIDATED a>=0
CK_T_B ENABLED NOT VALIDATED b>0
1.1.3. DISABLE&NOVALIDATE
7) c 字段创建 check 约束,条件为 c>0,表中 c 字段已存在数据 0,不符合 check 条件,不过,由于验证字段为 novalidate,状态为 disable,所以,原有的数据不进行验证,新增数据也不验证,这个 check 形同虚设
SQL> select * from t;
A B C D
---------- ---------- ---------- ----------
0 0 0 0
SQL> alter table t add constraint ck_t_c check(c>0)
2 disable novalidate;
Table altered.
SQL> insert into t(c) values(-1);
1 row created.
SQL> commit;
Commit complete.
SQL> select * from t;
A B C D
---------- ---------- ---------- ----------
0 0 0 0
-1
SQL> select constraint_name,status,validated,search_condition
2 from user_constraints where table_name='T';
CONSTRAINT_NAME STATUS VALIDATED SEARCH_CONDITION
-------------------- -------- ------------- --------------------
CK_T ENABLED VALIDATED a>=0
CK_T_B ENABLED NOT VALIDATED b>0
CK_T_C DISABLED NOT VALIDATED c>0
(Disabled是针对新插入数据的约束,validated是针对现有数据的约束)
1.1.4. DISABLE&VALIDATE
8) d 字段创建 check 约束,条件为 d>0,表中 d 字段已存在数据 0,不符合 check 条件,创建失败。
说明,在验证字段为 validate,状态为 disable 的情况下,对原有的数据进行验证,修改 check
条件为 d>=0,表中 d 字段已存在的数据 0 符合 check 条件,创建成功
SQL> select * from t;
A B C D
---------- ---------- ---------- ----------
0 0 0 0
-1
SQL> alter table t add constraint ck_t_d check(d>0)
2 disable validate;
alter table t add constraint ck_t_d check(d>0)
*
ERROR at line 1:
ORA-02293: cannot validate (SCOTT.CK_T_D) - check constraint violated
SQL>
SQL> alter table t add constraint ck_t_d check(d>=0)
2 disable validate;
Table altered.
——查看一下字典表,确认一下 STATUS 和 VALIDATED
SQL> select constraint_name,status,validated,search_condition from
2 user_constraints where table_name=upper('t');
CONSTRAINT_NAME STATUS VALIDATED SEARCH_CONDITION
-------------------- -------- ------------- --------------------
CK_T ENABLED VALIDATED a>=0
CK_T_B ENABLED NOT VALIDATED b>0
CK_T_C DISABLED NOT VALIDATED c>0
CK_T_D DISABLED VALIDATED d>=0
——往 d 字段中写入符合条件的记录 1,结果报错,提示信息很清楚,这种约束条件的字段不允许做insert/update/delete 操作
SQL> insert into t(d) values (1);
insert into t(d) values (1)
*
ERROR at line 1:
ORA-25128: No insert/update/delete on table with constraint (SCOTT.CK_T_D)
disabled and validated
通过以上的选项测试,我们了解到了创建约束的相关属性,也就是说,以后我们再创建约束,哪怕表中有
不符合约束的数据,那么,我们也会有相应办法来解决此问题。