4.4.2 not null约束 4.4.3 unique约束 4.4.4 check子句
not null约束写法
主码不用声明not null
4.4.3 unique约束
unique声明的属性形成候选码
unique中的属性可以为null
4.4.4 check子句
实例 在建表时指定check子句
验证
不满足check子句的插入会被拒绝
满足check子句的插入才会通过
目前check子句谓词不能是子查询
4.4.2 not null约束
正如我们在第3章中讨论过的,空值是所有域的成员,因此在默认情况下是SQL中每个属性的合法值。然而对于一些属性来说,空值可能是不合适的。
考虑student关系中的一个元组,其中name是null。这样的元组给出了一个未知学生的学生信息;因此它不含有有用的信息。
类似地,我们不会希望系的预算为null。
not null约束写法
在这些情况下,我们希望禁止空值,我们可以通过如下声明来通过限定属性name和budget的域来排除空值:
1 | name varchar(20) not null |
主码不用声明not null
not null声明禁止在该属性上插入空值。任何可能导致向一个声明为not null的属性插入空值的数据库修改都会产生错误诊断信息。
许多情况下我们希望避免空值。尤其是**SQL禁止在关系模式的主码中出现空值。因此,在我们的大学例子中,在department关系上如果声明属性dept_name为department的主码,那它就不能为空。因此主码(dept_name)不必显式地声明为not null**
4.4.3 unique约束
SQL还支持下面这种完整性约束:
1 | unique(A1,A2,...,An) |
unique声明的属性形成候选码
unique声明指出属性A1,A2,...,An形成了一个候选码;
即在关系中没有两个元组能在所有列出的属性A1,A2,...,An上取值相同。
unique中的属性可以为null
然而候选码属性可以为null,除非它们已被显式地声明为not null。
回忆一下,空值不等于其他的任何值。(这里对空值的处理与3.8.4节中定义的unique结构一样。)
4.4.4 check子句
当应用于关系声明时, check(P)子句指定一个谓词P,关系中的每个元组都必须满足谓词P。
**通常用check子句用来保证属性值满足指定的条件**。
实际上创建了一个强大的类型系统。例如,在创建关系department的create table命令中的check(budget>0)子句将保证budget上的取值是正数。
实例 在建表时指定check子句
作为另一个例子,考虑如下语句:
1 | create table section ( |
这里我们用check子句模拟了一个枚举类型,通过指定semester必须是’Fall‘、 Winter、 Spring或’ Summer‘中的一个来实现。这样, check子句允许以有力的方式对属性域加以限制。
验证
以下在MySQL 8.0中验证通过
不满足check子句的插入会被拒绝
1 | insert into section |
这个插入语句试图向semester属性赋值3333,这不满足check子句的要求,系统会拒绝插入操作.
1 | mysql> insert into section values('1111','2222','3333',2019,'大楼','4444','5555'); |
满足check子句的插入才会通过
1 | insert into section |
1 | mysql> insert into section values('1111','2222','Fall',2019,'大楼','4444','5555'); |
目前check子句谓词不能是子查询
根据SQL标准, check子句中的谓词可以是包括子查询在内的任意谓词。然而,当前还没有一个广泛使用的数据库产品允许check子句包含子查询的谓词。