主要是 约束 方面的基本知识
维护完整性的 3 种方法 :
- 应用代码保证 ( 有点悬,代码万一错误,数据完整性保证不了 ) 3 最后考虑使用
- trigger ( 缺点,开销比较大 ) 第 2 考虑使用
- constraint ( 性能高 , 开销小 ) 最优先考虑使用
unique 可以为空,并且同列多行都可以为空,因为 null 是无法比较的,所以也无法是相同的
- NOT NULL ( column 级别 )
定义 table 时可以直接创建 not null ( 通常来说,not null 是一个比较小的约束,所以不需要指定 约束名字 )
另外可以使用 alter table 再定义或删除之前的约束
ALTER TABLE orders MODIFY order_date NULL; -- 删除之前约束
ALTER TABLE orders MODIFY order_date NOT NULL; --增加了约束
- CHECK ( column 或 table 级别 )
可以在 check 中指定条件,必须是 boolean 表达式,可以指定同一行的其他列,但是不能使用其他行
有些函数不能使用 例如 ROWNUM, CURRVAL, NEXTVAL 等等
一列可以有多个 check
create table 中可以创建 check 约束
ALTER TABLE bounds ADD CONSTRAINT CK_NAME CHECK( salary > 0 );
- UNIQUE ( column 或 table 级别 )
可以多列组合成 UNIQUE 约束,最多32列组合在一起
oracle creates a unique index on the unique key columns to enforce uniqueness.
如果一个表有 1000万记录,如果一个列是UNIQUE的,那么插入时是不是要把1000W数据都确认一下,当然不是,这就是这个索引的作用。
如果在建立UNIQUE时,该列已经存在索引了,那么 oracle 可以使用该索引
UNIQUE准许约束列有 NULL
ALTER TABLE a ADD CONSTRAINT UQ_NAME UNIQUE( DEPT, EMP_ID)
USING INDEX TABLESPACE INDX
STORAGE( …
ALTER TABLE a ADD SSN VARCHAR2(11) CONSTRAINT UQ_SSN UNIQUE;
- PRIMARY KEY ( table 级别 )
UNIQUE + NOT NULL = PRIMARY KEY
A table can have only one primary key.
ORACLE creates a unique index and NOT NULL constraints for each column in the key.
Indexes created to enforce unique keys and primary keys can be managed as any other index, however, these indexes cannot be dropped
这是当然,因为相应的index 是因为 约束而自动创建的,如果随意就删除了该索引,那么约束怎么办。
- FOREIGN KEY ( column 级别 和 table 级别 )
子表中的某列参考父表的unique 列或 primary key 列
foreign key column and reference key column 可以是同一个表
NULL values are allowed in the foreign key columns.
ALTER TABLE city ADD CONSTRAINT FK_NAME FOREIGN KEY (COUNTRY_CODE, STATE_CODE) REFERENCES STATE( COUNTRY_CODE, STATE_CODE);
foreign key , references key 同一个 table
DELETE NO ACTION ( 删除或更新父表值的时候,违反了约束,不可以) 默认
DELETE CASCADE ( 删除父表的数据,那么子表中相应数据也会被删除 )
DELETE SET NULL ( 当你删除父表中的数据时,将子表中对应的外键被设置成 NULL)
语句写法 ON DELETE CASCADE / ON DELETE SET NULL
高级部分
ALTER TABLE emp ENABLE PRIMARY KEY; 将某个约束设置成 enable
DROP CONSTRAINS
ALTER TABLE a DROP CONSTRAINT CK_name;
ALTER TABLE a DROP UNIQUE(EMP_ID) CASCADE;
ALTER TABLE a DROP PRIMARY KEY CASCADE; cascade 级联,将外键也给干掉
disable , enable 是对未来要插入本表的, 对表中已经存在的数据,那么就是 validate 有效或 novalidate 无效
ENABLE : if a constraint is enabled, data is checked as it is entered or updated in the database.
DISABLE : If a constraint is disabled, then data that does not confirm can be entered into the database.
4 种状态 :
When a constraint changes to enable validate from a disable state, the table is locked and all data in the table is checked for conformity. This may cause DML operations such as a data load to wait, so it is advisable to move first from a disable state to enable novalidate, and then to enable validate.
当你要将状态从 disable novalidated 转换到 enable vaildated, 分两步,先将状态改成 enable novalidated-> enable validated
规则如下 :
当你指定 ENABLE 时 默认就指定 VALIDATE , 除非之前先指定 NOVALIDATE
当你指定 DISBALE 时 默认指定 NOVALIDATE, 除非之前先指定 VALIDATE
当你将 NOVALIDATE 状态调整到 VALIDATE 状态时,所有的数据都会被确认一遍
ALTE TABLE t ENABLE NOVALIDATE PRIMARY KEY , 此时,会自动创建唯一性索引,所以,如果此时你表中已经包含了违反约束的内容,比如两条完全一样的数据,那么这条命令就会不成功。
当导入大量数据时
No locks are held.
All constraints can go to enable state concurrently
Constraint enabling is done in parallel
Concurrent activity on table is permitted.
检查时间
默认是 nondeferred , 不能互相转换,即 noderred 不能变成 deferred, 这个并不意味着就是稍后检查
nondeferred or immedate constraints : 是执行 DML 之后,立刻确认约束,就会提示。当我们执行DML时,首先会在本地看到改变情况,这个时候我们并没有提交 commit, 此时,如果触犯了约束,那么就会提示。
deferred : are checked only when a transaction is commited , 就是说,你修改或者插入,你如果不提交是成功的,不会去确认,只有提交的时候,才确认。 If any constraint violations are detected at commit time, the entire transaction is rolled back.These constraints are most useful when both the parent and child rows in a foreign key relationship are entered at the same time, as in the case of an order entry system, where the order and the items in the order are entered at the same time. ( 这种情况,如果是 immedate 约束就无法插入,而如果是 deferred 就可以插入数据 )
Initially immediate specifies that by default it should function as an immediate constraint, unless explicitly set otherwise.
Initially deferred specifies that by default the constraint should only be enforced at the end of the transaction.
可以很对特殊的 transaction 设置 检查约束是立刻还是提交前, 也可以通过 alter session 来指定session 来确定当前是 immediate 还是 deferred.
primary key 约束,如果是 dererred 创建,则创建的约束会自动创建一个非 unique 索引
判断 primary key 和 unique key 时:
通常要在子表的 foreign key 这列要建立索引, 因为如果要在主表中要删除某个 key , 那么,它要判断在字表中的 foreign key 这列是否有该值,如果没有,那么就可以删除,所以,如果 foreign key 没有索引的。那么就。。。 而且使用的是表级锁,将整个表都锁住
以上内容,如果反着插入的话,就不能插入。( 自己 reference 自己 )
好处 :
All constraints are enabled concurrently.
Each constraint is internally parallelized
Concurrent activity on the table is permitted.
DATA DICTIONARY
DBA_CONSTRAINTS
DBA_CONS_COLUMNS