mysql--表的约束

目录

理解表的约束和操作

如何理解?

1、空属性null

2、默认值default

3、列描述comment

4、自动填充zorefill

[5、主键primary key](#5、主键primary key)

(1)创建表时指定可以

(2)创建表后指定key

(3)删除主键列:

(4)复合主键

[6、自增长 auto_incremen](#6、自增长 auto_incremen)

7、唯一键unique

8、外键

9、学以致用---综合案例练习

约束类型 说明 示例
primary key 唯一标识表中的每一行,不能有重复值,且不能为空。 primary key (id)
foreign key 确保表中的数据与另一表中的数据相关联,通常用于实现表之间的关系。 foreign key (user_id) references users(id)
unique 确保列中的所有值都是唯一的,允许空值,但每个非空值必须唯一。 unique (email)
not null 确保列中的数据不能为空。 name VARCHAR(255) not null
check 确保列中的值满足特定条件。注意:在 MySQL 的某些版本中,check 约束可能不会被强制执行。 check (age >= 18)
default 为列指定默认值,如果插入行时未提供该列的值,则使用默认值。 age INT default 18
auto_increment 使列的值在插入时自动增加,通常用于主键。 id INT auto_increment primary key
index 用于加速查询,创建一个索引以提高检索数据的速度。 index (last_name)

如何理解?

对表的理解:数据库的每一张表相当于C语言中的结构体,是对现实事务的描述,通过属性和对应数据进行描述

表中一定要有各种约束,通过约束,使得在插入数据时符合预期。

如果插入错误数据(无论有意无意),就报错,不让插入,以此倒逼写对,这就是约束。

如此,就保证凡是插入成功的数据都是符合数据规则的,符合约束的。

因此,为了更好的保证数据的完整性和可预期性,

于是对一个数据库的表设置一系列约束

这就是约束的目的。

1、空属性null

两个值:null(默认值)和 not null(不为空)

在mysql,null表示什么都没有,大小写不区分

在mysql,单引号''和双引号""都表示字符串

not null什么意思?

意思是:这一列不能为空,必须有值

如果你插入为空,报错

怎么用?

跟在创建列的后面,不写默认为null,表示可以为为空

如果不可为空,就要加上not null,表示不可以为空,非空约束

案例如下:

cpp 复制代码
create table student(
id int not null,
name varchar(10) not null
gender char(1) not null
);

2、默认值default

默认值的意义:当插入数据候,未指定数据,就用默认值;如设置了值,则使用新值,类似于缺省

cpp 复制代码
default xxx,#跟在创建列的后面

情况1:设置了not null 但是没有设置default默认值

如果插入为空,此时插入报错,因为没有默认值

实例:

cpp 复制代码
create table table7 (
id int not null
);
cpp 复制代码
insert into table7 values ();

情况2:设置了not null 且设置有default默认值

如果插入为空,此时插入成功,因为即使没有插入,也可以使用默认值

实例:

cpp 复制代码
create table table6(
id int not null default 1
);
cpp 复制代码
insert into table6 values ();

情况3:什么约束都没有

如果省略插入,此时应该报错;因为我们没有指定默认值

可是事实是,mysql帮我们加了上去

实例:

cpp 复制代码
create table table8 ( id int );
cpp 复制代码
insert into table8 values ();

查看系统默认加上的情况:

cpp 复制代码
show create table table8 \G;

具体情况具体分析

3、列描述comment

列描述:comment,没有实际意义,用来描述字段。

根据表创建语句时保存,用于注释解释

有什么用呢?其实就是注释,给程序员看的。

通过desc查不到这个注释信息

cpp 复制代码
create table people(
name varchar(32) comment '人的名字'
);

怎么查看:

cpp 复制代码
show create table table_name;

4、自动填充zorefill

cpp 复制代码
create table table9 ( 
id int(5) zerofill
);
cpp 复制代码
insert into table9  values (1);

作用:当插入值的宽度小于设定宽度,自动在前面添加0

它仅仅只是一种显示格式,实际的数据存储并没有改变,什么都不会影响

那么int(10)这个括号里面的10是什么意思呢? 也没有什么意义。就是一个数字的显示长度

10表示宽度设置为10,如果加上zerofill约束,如果插入的数字不够10位,那么就会自定填补为10位

注意,如果插入的数据超过10位其实也不会影响。

所以,可以不必在意,没有什么用处。

5、主键primary key

主键是用来约束一行字段唯一性的数据,不能重复,不能为空

一张表中最多只能有一个主键

什么意思?

一张表中有很多行,但是如何标识唯一性?用主键来表示

主键是一个列属性,通常是一个整数类型

例如你的学号。

在学生数据库中,有很多属性,例如年龄、性别、姓名、年级、籍贯等

但是,如果确定一个学生的唯一性呢?

如果同时有两个张三?

同一个地方的?

用学号标识学生的唯一性

于是,你的学号就是你这一行信息的主键

有了主键之后,我们就可以对主键直接查询,就可以查询到对应的数据行

(1)创建表时指定可以

cpp 复制代码
create table table10(
id int primary key
);

(2)创建表后指定key

cpp 复制代码
alter table table_name add peinmary key(filed_name);

示例:

cpp 复制代码
alter table table11 add primary key (id);

注意:这种情况要保证这一列没有重复数据,否则无法指定

(3)删除主键列:

cpp 复制代码
​
alter table table_name drop primary key;

​

(4)复合主键

主键并不知仅仅只能一列,而是可以多列

例如,(id, name)的组合

此时,只有两个列的数据同时重复,才会显示冲突

cpp 复制代码
 primary key(id, name);#单独作为一列
cpp 复制代码
alter table table12 add primary key (id,name);

6、自增长 auto_incremen

auto_incremen;#跟在对应列的后面

cpp 复制代码
create table table13 ( id int auto_increment primary key);

查询最后一行自增数据:

cpp 复制代码
select last_insert_id();

auto_incremen:对应字段不给值,会自动+1,即自增

特点:需要设置为主键

自增长必须是整数

一张表最多一个自增长

自增时,从最大索引开始增加

可以插入比当前最大索引大的值

但是不可以插入重复值,因为是主键

可以设置起始值,自增将从该值开始

如果没有设置起始值,默认为0

实例:

7、唯一键unique

特点:

唯一键可以为空,但主键不能为空

唯一键也可以设置为非空

cpp 复制代码
unique;#跟在对应属性列后面
cpp 复制代码
create table table14( id int primary key, name varchar(32) unique );

如何理解?

主键用于标识一组数据在所有数据组中具有唯一性

唯一键也是用于标识某一列的数据的唯一性

二者是不是冲突了?

并非如此

那么要怎么理解呢?

举个例子:学校的学生信息数据

一般以学号作为主键,标识一个学生在学校的唯一性,这很好理解。

但是,假设学生的信息还有身份证和微信号

此时,因为主键每一个表只能设置一个列

因此,身份证和微信号可以重复

但是,我们知道,两个人的身份证和微信号绝对不可能重复

如果数据表在设计的时候,没有对这些敏感数据进行约束

即没有规定不可以重复

那么就有可能因为其他因素导致数据的重复

导致数据错误

所以,仅仅一个设置一个主键,仅仅能保证一个学生在学校的唯一性

但是却不能保证该学生的其他数据也具有唯一性

所以,唯一键就来了

如果此时,我们对身份证和微信号设置了唯一键

那么,就可以避免错误重复

这就是唯一键和作用

主键确保数组组的在整体的唯一性

唯一键确保数据组中某一数据的唯一性

二者是不想补充的,而非冲突,也并非重复

那么,有了主键和唯一键能不能完全避免错误?

不可以,因为只是确保不重复

没有确保你录入错误信息.....

加入一个列属性已经设置为空,而且有很多数据已经是空了

如果此时再修改表,将之属性设置为非空,此时会发生什么?

答:在尝试将列属性从允许 NULL 修改为 NOT NULL 时,如果该列中存在 NULL 值,MySQL 会阻止该操作并返回错误。为了成功完成这一操作,需要先处理所有现存的 NULL 值,确保符合新约束。

8、外键

特点:

强调表与表之间的约束关系

设置为外键的一般是从表

设置为外键的属性列必须再主表的主键列 或者 为null

可以为外键约束加上名字,类似于comment

语法是:constraint '外键约束名'

设置外键约束,被关联的表必须有索引,可以理解为有主键。

cpp 复制代码
foreign key (字段名) references 主表(列)

如何理解?

如果一张表的属性太多,就会显得十分的冗余,同时也不好管理

因此,描述一个事物不可避免地会出现多个表来分别描述的问题

同时,分开描述也可以让一个事物的某些特征聚合管理,使得相关性更加灵活的分布

但是,分开管理,是不是就各自管理,不管其他的死活了呢?

不是的

举个例子:

描述一个学生,有两张表:

一张表是学生信息描述表,专门描述学生的个人信息

一张是学生隶属的班级表,专门记录班级人数、性别比例、整体信息等

上述将两个表分开描述,你会发现各司其职,很清爽,不冗余

一般来说,学生是隶属于班级的,因此学生应该作为从表,依附于班级表

假设,你是信息学院的,你们有四个班,分别是计科1班、计科2班、计科3班、计科4班

此时,学生信息表中有一个属性,叫做class_id,标识你是哪个班的

现在,有一个人,他叫张三,张三录入信息的时候,手抖了一下

把他的班级号录成了10.

???

很明显,是错的,没有10班

再比如,计科1班有100个学生在读,

此时数据库管理员不小心,把计科1班这个表直接删除了

很明显,也是错的,学生还没毕业呢,不应该删除

所以你会发现,将表分开管理,确实很清爽

但是问题也随之而来

两个孤立的表,如果不联系,会有很多问题

因此,数据库需要保证数据的安全和完整性

就要进行约束

怎么约束?

表与表之间的约束,使用外键约束

外键别的本质:产生关联、产生约束、保证表与表之间的完整性

实例:学生隶属于班级

创建班级表:

cpp 复制代码
create table class(
id int primary key 
);

创建学生表并添加外键约束:

cpp 复制代码
create table student( 
id int, 
name varchar(32), 
class_id int, 
foreign key (class_id) references class(id) );

9、学以致用---综合案例练习

相关推荐
Sunyanhui12 小时前
牛客网 SQL36查找后排序
数据库·sql·mysql
老王笔记2 小时前
MHA binlog server
数据库·mysql
m0_548514773 小时前
2024.12.10——攻防世界Web_php_include
android·前端·php
凤邪摩羯3 小时前
Android-性能优化-03-启动优化-启动耗时
android
凤邪摩羯3 小时前
Android-性能优化-02-内存优化-LeakCanary原理解析
android
2401_871213303 小时前
mysql高阶语句
数据库·mysql
喀什酱豆腐4 小时前
Handle
android
山山而川粤5 小时前
网络安全宣传系统|Java|SSM|JSP|
java·开发语言·后端·学习·mysql
m0_748232925 小时前
Android Https和WebView
android·网络协议·https
m0_748251726 小时前
Android webview 打开本地H5项目(Cocos游戏以及Unity游戏)
android·游戏·unity