MySQL表的约束

MySQL表的约束

  • 表中一定要有各种约束,通过约束,让我们未来插入数据库表中的数据是符合预期的。约束的本质: 通过技术手段,倒逼程序员,插入正确的数据。反过来,站在MySQL的视角,凡是插入进来的数据,都是符合数据约束的!

  • 约束的最终目标:保证数据的完整性和可预期性

真正约束字段的是数据类型,但是数据类型约束很单一,需要有一些额外的约束,更好的保证数据的合法性,从业务逻辑角度保证数据的正确性。比如有一个字段是email,要求是唯一的。

表的约束很多,这里主要介绍如下几个: null/not null,default, comment, zerofill,primary,key,auto_increment,unique key。

1. 空属性

  • 两个值:null(默认的)和not null(不为空)
  • 数据库默认字段基本都是字段为空,但是实际开发时,尽可能保证字段不为空,因为数据为空没办法参与运算

在这里插入图片描述

创建一个班级表,包含班级名,班级所在的教室,班级类型;前两个字段不能为空,创建时带上not null选项,后一个字段没有要求。

创建后,查看这张表发现,前两个字段是否允许列为空Null那一列写的是NO,后一个字段那一列写的是YES;

查看表创建时的详细信息,前两个字段那里有 NOT NULL,最后一个字段是DEFAULT NULL(下面解释)

在这里插入图片描述

向其中插入数据,此时3个字段均有值,可以成功插入

在这里插入图片描述

下面的方式插入字段,省略最后一个字段可以插入成功

将前两个字段(不能为空)中任意一个设为NULL, 就会报错

在这里插入图片描述

2. 默认值(default)

  • 默认值:某一种数据会经常性的出现某个具体的值,可以在一开始就指定好,在需要真实数据的时候,用户可以选择性的使用默认值。

  • 默认值的生效:数据在插入的时候不给该字段赋值,就使用默认值

创建一张表,设置3个字段,姓名设为不可为空;年龄设置为给默认值,性别设置为不为空可以给默认值

创建后查看这张表,会发现Default这一列后两个字段有默认值,Null这一列age是YES, gender是NO,符合我们我们的预期。

在这里插入图片描述

查看表创建时的详细信息,也能看到

在这里插入图片描述

向表中插入数据时,如果不指明用户的年龄或性别,那么就会使用对应的默认值(缺省值)

在这里插入图片描述

解释一个字段同时设置not nulldefault两个值

  • default:如果设置了,用户将来插入,有具体的数据,就用用户的,没有就用默认的

  • 如果我们没有明确指定一列要插入,用的是default;如果建表中,对应列默认没有设置default值,无法直接插入

在这里插入图片描述

这里同时设置not nulldefault的意义:

用户想要插入只能插入合法数据,不能为NULL; 如果用户没有把这一列带上,就是用明确的default值

在这里插入图片描述

  • default不冲突,而是互相补充;
    • NOT NULL主要约束当用户想插入数据时,只能插入合法数据,不能插入NULL
    • default主要约束当用户忽略这一列时,使用默认值(如果设置了),如果没有设置默认值则直接报错

3. 列描述(comment)

列描述:comment,没有实际含义,专门用来描述字段,会根据表创建语句保存,用来给程序员或DBA来进行了解,相当于语言学习中的注释。

比如创建一个表,表当中包含用户名、用户的年龄和用户的性别,在每一个字段后面添加上对应的列描述

在这里插入图片描述

创建之后,查看表创建时的详细信息(通过desc查看不到注释信息)

在这里插入图片描述

4. zerofill

数值类型后面的圆括号中的数字,代表的是显示宽度,数值类型设置zerofill属性后,如果数据的宽度小于设定的宽度则自动填充0,否则正常显示。

创建一张表,数据类型是int,不写后面的圆括号,默认创建后圆括号显示是10

在这里插入图片描述

向这张表插入数据,正常显示

在这里插入图片描述

修改表结构,给b列添加上zerofill属性,由于a列数据的显示宽度为10,因此查看表中数据可以看到a列数据中宽度不足10位的数据都自动在前面填充0

在这里插入图片描述

我们在向其中插入数据,还是刚才的显示规则,这是我们去查找值为200的,后发现查找到的是b;

证明了:设置了zerofill属性后的只是对原来数值的一种格式化输出,在MySQL中实际存储的还是原来的数值

在这里插入图片描述

同时设置了zerofill属性对存储的数据并不影响

将上面的int(10)修改为int(4)

在这里插入图片描述

后向其中插入一些值,不足4位不0填充,超过4位正常显示

在这里插入图片描述

5. 主键(primary key)

  • 主键:primary key用来唯一的约束该字段里面的数据,不能重复,不能为空,一张表中最多只能有一个

  • 主键:主键所在的列通常是整数类型。

  • 创建表的时候直接在字段上指定主键

创建一张表,给学生id属性后面加primary key, 查表时会发现id这一字段有PRI的字样

在这里插入图片描述

  • 主键约束:主键对应的字段中不能重复,一旦重复,操作失败

向其中插入数据,一旦id重复就会报错

在这里插入图片描述

需要注意:只有列当中的值不为空并且不重复的列才能被设置成主键,如果列中已经有了重复的的值,则设置主键失败。这也说明要先把表结构设计好,不然后面插入有数据很难进行操作。

  • 删除主键
alter table 表名 drop primary key;
  • 当表创建好以后但是没有主键的时候,可以再次追加主键
alter table 表名 add primary key(字段列表)

在这里插入图片描述

  • 复合主键
    在创建表的时候,在所有字段之后,使用primary key(主键字段列表)来创建主键,如果有多个字段作为主键,可以使用复合主键。

创建一张表,将id和课程id设为复合主键

在这里插入图片描述

向表中插入数据时,只有插入的学生ID和课程ID同时出现冲突时才会产生主键冲突,否则就允许插入

在这里插入图片描述

6. 自增长(auto_increment)

auto_increment:当对应的字段,不给值,会自动的被系统触发,系统会从当前字段中已经有的最大值+1操作,得到一个新的不同的值。通常和主键搭配使用,作为逻辑主键

自增长的特点:

  • 任何一个字段要做自增长,前提是本身是一个索引(key一栏有值)
  • 自增长字段必须是整数
  • 一张表最多只能有一个自增长

创建一张表,将id这一字段设为主键,同时带上auto_increment选项,创建后查看表,Extra这一列会有auto_increment

在这里插入图片描述

向表中插入第一条记录时如果没有指明自增长字段的值,那么自增长字段的值默认将会从1开始。id不给值,会自动的被系统触发,系统会从当前字段中已经有的最大值+1操作,得到一个新的不同的值。

后续向表中插入不指明自增长字段的值,则自增长的值就会依次递增

在这里插入图片描述

如果指明了自增长的值,就会插入这个指明的值

在这里插入图片描述

如果后续插入还是不指明自增长的值,这次插入就会在上次插入的基础上自增长

在这里插入图片描述

其实原理很简单,查看创建表的详细信息,这里就会保存下一次自增长的值

在这里插入图片描述

同时在创建表时,也可以自己指明自增长的值,此时插入数据就会以此值为基础自增长

在这里插入图片描述

last_insert_id();获取最后一个自增长的值

在这里插入图片描述

一个自增长应用的例子:

比如用户注册QQ号时腾讯内部会向这个用户返回QQ账号,此账号是一个唯一值,它的原理: 相当于向数据库后台插入一条记录,数据库后台把用户QQ这个字段设置了自增长

7. 唯一键(unique key)

  • 一张表中有往往有很多字段需要唯一性,数据不能重复,但是一张表中只能有一个主键:唯一键就可以解决表中有多个字段需要唯一性约束的问题。

  • 唯一键的本质和主键差不多,唯一键允许为空,而且可以多个为空,空字段不做唯一性比较

  • 关于唯一键和主键的区别:我们可以简单理解成,主键更多的是标识唯一性的。而唯一键更多的是保证在业务上,不要和别的信息出现重复。

创建一张表,将id设为主键,电话号码和qq号设为唯一键,查看表就会发现Key一列是唯一键的有UNI字样

在这里插入图片描述

向其中插入值,除主键外,对于电话号码和qq号2个唯一键有任意一个值相同都会因为唯一键冲突插入失败,只有两者完全不同才会插入成功

在这里插入图片描述

同时唯一键允许插入为空

在这里插入图片描述

8. 外键(foreign key)

外键用于定义主表和从表之间的关系:外键约束主要定义在从表上,主表则必须是有主键约束或unique约束。当定义外键后,要求外键列数据必须在主表的主键列存在或为null。

语法:

foreign key (字段名) references 主表()

首先创建一张这样的班级表

在这里插入图片描述

再创建一个学生表,表当中包含学生的id、姓名以及学生所在班级对应的id,学生id设为主键,班级id设为外键

表创建成功后查看表,学生表中的班级id对应的Key列出现了MUL,这表明class_id已经成功被设置成了外键

在这里插入图片描述

向学生表中插入记录时,如果插入的记录对应的班级id是班级表中存在的,或者插入的班级id为null,那么此时是允许进行插入的。

在这里插入图片描述

如果插入一个完全不存在的班级id,是不允许插入的

在这里插入图片描述

在这里班级表是主表,学生表是从表,让class_id和id形成关联的关系,这就是外键约束。

在这里插入图片描述

9. 综合案例

有一个商店的数据,记录客户及购物情况,有以下三个表组成:

  • 商品goods(商品编号goods_id,商品名goods_name, 单价unitprice, 商品类别category, 供应商provider)
  • 客户customer(客户号customer_id,姓名name,住址address,邮箱email,性别sex,身份证card_id)
  • 购买purchase(购买订单号order_id,客户号customer_id,商品号goods_id,购买数量nums)

要求:

  • 每个表的主外键
  • 客户的姓名不能为空值
  • 邮箱不能重复
  • 客户的性别(男,女)
-- 创建数据库
create database if not exists bit32mall
default character set utf8 ;
-- 选择数据库
use bit32mall;
-- 创建数据库表
-- 商品
create table if not exists goods
(
goods_id int primary key auto_increment comment '商品编号',
goods_name varchar(32) not null comment '商品名称',
unitprice decimal not null default 0 comment '单价,单位分',
category varchar(12) comment '商品分类',
provider enum('供应商A','供应商B') not null comment '供应商名称'
);
-- 客户
create table if not exists customer
(
customer_id int primary key auto_increment comment '客户编号',
name varchar(32) not null comment '客户姓名',
address varchar(256) comment '客户地址',
email varchar(64) unique key comment '电子邮箱',
sex enum('男','女') not null comment '性别',
card_id char(18) unique key comment '身份证'
);
-- 购买
create table if not exists purchase
(
order_id int primary key auto_increment comment '订单号',
customer_id int comment '客户编号',
goods_id int comment '商品编号',
nums int default 1 comment '购买数量',
foreign key (customer_id) references customer(customer_id),
foreign key (goods_id) references goods(goods_id)
);
  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值