oracle中的约束
2015-08-11 16:20
465 查看
概述:数据的完整性用于确保数据库数据遵从一定的商业和逻辑规则。在Oracle中,数据完整性可以使用约束、触发器、应用程序(过程、函数)三种方法来实现,在这三种方法中,因为约束易于维护,并且具有最好的性能,所以作为维护数据完整性的首选。
SQL 约束
约束用于限制加入表的数据的类型。可以在创建表时规定约束(通过 CREATE TABLE 语句),或者在表创建之后也可以(通过 ALTER TABLE 语句)。
我们将主要探讨以下几种约束:
NOT NULL
UNIQUE
PRIMARY KEY
FOREIGN KEY
CHECK
DEFAULT
1.NOT NULL 约束
NOT NULL 约束强制列不接受 NULL 值。NOT NULL 约束强制字段始终包含值。这意味着,如果不向字段添加值,就无法插入新记录或者更新记录。
下面的 SQL 语句强制 "Id_P" 列和 "LastName" 列不接受 NULL 值:
CREATE TABLE Persons ( Id_P int NOT NULL , LastName varchar(255) , FirstName varchar(255) , Address varchar(255), City varchar(255) )
2.UNIQUE 约束
UNIQUE 约束唯一标识数据库表中的每条记录。UNIQUE 和 PRIMARY KEY 约束均为列或列集合提供了唯一性的保证。
PRIMARY KEY 拥有自动定义的 UNIQUE 约束。
请注意,每个表可以有多个 UNIQUE 约束,但是每个表只能有一个 PRIMARY KEY 约束。
在创建表时时,创建UNIQUE约束:
CREATE TABLE Persons ( Id_P int NOT NULL UNIQUE , LastName varchar(255) NOT NULL, ...... )
若为几列同时设定UNIQUE约束:
CREATE TABLE Persons ( Id_P int NOT NULL, ...... City varchar(255), CONSTRAINT uc_PersonID UNIQUE (Id_P,LastName) )
若表已经创建好,现在想添加约束:
ALTER TABLE Persons ADD UNIQUE (Id_P)
若需要命名约束,且需要定义多个列的UNIQUE约束:
ALTER TABLE Persons ADD CONSTRAINT uc_PersonID UNIQUE (Id_P,LastName)
如需撤销 UNIQUE 约束,请使用下面的 SQL:
ALTER TABLE Persons DROP CONSTRAINT uc_PersonID
3.主键约束
PRIMARY KEY 约束唯一标识数据库表中的每条记录。
主键必须包含唯一的值。
主键列不能包含 NULL 值。
每个表都应该有一个主键,并且每个表只能有一个主键。
主键可以是一列,也可以是几列。
在创建表时设置主键:
CREATE TABLE Persons ( Id_P int NOT NULL PRIMARY KEY, ...... City varchar(255) )
在创建表时设置主键并命名:
CREATE TABLE Persons ( Id_P int NOT NULL , ...... CONSTRAINT pk_PersonID PRIMARY KEY (Id_P,LastName) )
表已经建立好,现在创建约束:
不命名: ALTER TABLE Persons ADD PRIMARY KEY (Id_P) 命名: ALTER TABLE Persons ADD CONSTRAINT pk_PersonID PRIMARY KEY (Id_P,LastName)
注释:如果您使用
ALTER TABLE 语句添加主键,必须把主键列声明为不包含 NULL 值(在表首次创建时)。
撤销PRIMARY KEY 约束:
ALTER TABLE Persons DROP CONSTRAINT pk_PersonID
4.FOREIGN
KEY约束
一个表中的 FOREIGN KEY 指向另一个表中的 PRIMARY KEY。
"Persons" 表:
Id_P | LastName | FirstName | Address | City |
---|---|---|---|---|
1 | Adams | John | Oxford Street | London |
2 | Bush | George | Fifth Avenue | New York |
3 | Carter | Thomas | Changan Street | Beijing |
Id_O | OrderNo | Id_P |
---|---|---|
1 | 77895 | 3 |
2 | 44678 | 3 |
3 | 22456 | 1 |
4 | 24562 | 1 |
FOREIGN KEY 约束也能防止非法数据插入外键列,因为它必须是它指向的那个表中的值之一。
1.下面的
SQL 在 "Orders" 表创建时为 "Id_P" 列创建 FOREIGN KEY:
CREATE TABLE Orders ( Id_O int NOT NULL PRIMARY KEY, Id_P int FOREIGN KEY REFERENCES Persons(Id_P) )
如果需要命名 FOREIGN KEY 约束,以及为多个列定义 FOREIGN KEY 约束,请使用下面的 SQL 语法:
CREATE TABLE Orders ( Id_O int NOT NULL, PRIMARY KEY (Id_O), CONSTRAINT fk_PerOrders FOREIGN KEY (Id_P) REFERENCES Persons(Id_P) )
如果在
"Orders" 表已存在的情况下为 "Id_P" 列创建 FOREIGN KEY 约束,请使用下面的 SQL:
ALTER TABLE Orders ADD FOREIGN KEY (Id_P) REFERENCES Persons(Id_P)
如果需要命名 FOREIGN KEY 约束,以及为多个列定义 FOREIGN KEY 约束,请使用下面的 SQL 语法:
ALTER TABLE Orders ADD CONSTRAINT fk_PerOrders FOREIGN KEY (Id_P) REFERENCES Persons(Id_P)
撤销 FOREIGN KEY 约束
ALTER TABLE Orders DROP CONSTRAINT fk_PerOrders
5.CHECK约束
CHECK 约束用于限制列中的值的范围。如果对单个列定义 CHECK 约束,那么该列只允许特定的值。
如果对一个表定义 CHECK 约束,那么此约束会在特定的列中对值进行限制。
创建表时,设置check约束:
CREATE TABLE Persons ( Id_P int NOT NULL , ....... )
如果需要命名 CHECK 约束,以及为多个列定义 CHECK 约束,请使用下面的 SQL 语法:
CREATE TABLE Persons ( Id_P int NOT NULL, ....... )
如果在表已存在的情况下为
"Id_P" 列创建 CHECK 约束,请使用下面的 SQL:
不命名: ALTER TABLE Persons ADD CHECK (Id_P>0) 命名: ALTER TABLE Persons ADD CONSTRAINT chk_Person CHECK (Id_P>0 AND City='Sandnes')
撤销check约束:
ALTER TABLE Persons DROP CONSTRAINT chk_Person
6.DEFAULT 约束
创建表时:
CREATE TABLE Persons ( Id_P int NOT NULL, ...... City varchar(255) DEFAULT 'Sandnes' )
通过使用类似 GETDATE() 这样的函数,DEFAULT 约束也可以用于插入系统值:
CREATE TABLE Orders ( Id_O int NOT NULL, ....... OrderDate date DEFAULT GETDATE() )
撤销:
ALTER TABLE Persons ALTER COLUMN City DROP DEFAULT
案例:
商品售货系统表设计案例
现在有一个商店的数据库,记录客户及其购物情况,由下面三个表组成:
商品表Goods(商品号GoodsId,商品名GoodName,单价UnitPrice,商品类别Categroy,供应商Provider)
客户表Customers(客户号CustomerId,姓名Name,住址Address,电邮Email,性别Gender,身份证CardId)
销售表Purchases(客户号CustomerId,商品号GoodsId,购买数量Num)
请用SQL语言完成下列功能:
建表,在定义中要求声明:
(1)每个表的主外键。
(2)客户的姓名不能为空值。
(3)单价必须大于0,购买数量必须在1~30之间。
(4)电邮不能够重复。
(5)客户的性别必须是男或女,默认是男。
sql>create table Goods(
GoodsId char(8) primary key ,--主键
GoodName varchar2(50),
UnitPrice number(10,2) check(UnitPrice>0),--单价必须大于0
Category varchar(30),
Provider varchar(100));
sql>create table Customers(
CustomerId char(8) primary key,
Name varchar2(30) not null, --姓名不能为空
Address varchar2(150),
Email varchar2(100) unique,--必须唯一
Gender char(2) default('男') check(Gender in('男','女')),
CardId char(18));
sql>create table Purchases(
CustomerId char(8) references Customers(CustomerId), --外键
GoodsId char(8) references Goods(GoodsId),
Num number(10) check(Num between 1 and 30)));
2、添加约束
如果在建表时忘记建立必要的约束,则可以在建表后使用alter table命令为表增加约束,但是要注意:增加not null约束时,需要使用modify选项,而增加其他四种约束使用add选项。
(1)增加商品名也不能为空
sql>alter table Goods modify GoodsId not null;
(2)增加身份证也不能重复
sql>alter table Customers add constraint UQ_CardId unique(CardId);
(3)增加客户的住址只能是海淀、朝阳、东城、西域
sql>alter table Customers add constraint CK_Address check(Address in ('海淀','朝阳','东城','西域'));
3、删除约束
当不再需要某个约束时,可以删除。
sql>alter table 表名 drop constraint 约束名称;
特别说明:
在删除主键约束的时候,可能有错误。比如
sql> alter table 表名 drop primary key;
这是因为如果在两表存在主从关系,那么在删除主表主键约束时,必须带上cascade选项。
sql> alter table 表名 drop primary key cascade;
4、显示约束信息
A、显示约束信息
通过查询数据字典视图user_constraints,可以显示当前用户所有的约束的信息。
sql>select constraint_name,constraint_type,status,validated from user_constraints where table_name='Goods';
B、显示列约束
通过查询数据字典视图user_cons_column,可以显示约束所对应的表列信息。
sql>select column_name,position from user_cons_columns where constraint_name='CK_Address';
6、表级定义和列级定义
A、表级定义
表级定义是指在定义了所有列后,再定义约束,这里需要注意,not null约束只能在列级上定义。
案例:
sql> create table Goods(
GoodsId char(8),GoodsName varchar2(50), Category varchar(30),
constraint PK_GoodsId primary key(GoodsId));
B、列级定义
列级定义是在定义列的同时定义约束。
案例:
sql>create table Goods(
GoodsId char(8) constraint PK_GoodsId primary key ,--主键
GoodsName varchar2(50),
UnitPrice number(10,2) check(UnitPrice>0),--单价必须大于0
Category varchar(30),
Provider varchar(100));
相关文章推荐
- Oracle的监听(listener)到底是什么
- oracle客户端安装
- oracle中的decode的使用
- 再记录一下如何配置oracle instantclient
- Oracle无法操作只能查询:record is locked by another user
- ORACLE USERENV函数
- oracle11g 密码过期问题
- Oracle SQL优化 总结
- oracle 储存过程
- oracle join on 连接
- ORACLE PARTITION
- ORACLE11G安装教程
- oracle 真正去重效率语句
- oracle range分区表已经有了MAXVALUE 分区,如何添加分区?要不能删除MAXVALUE分区里的数据,不影响在线应用。
- ORACLE最大连接数问题
- oracle 存储过程 基础
- Oracle数据库优化
- Oracle 12C -- 在相同的列的集合上创建多个索引
- Oracle11g修改默认用户密码有效期时间
- 安装oracle