一、空属性
两个值:null(默认的)和not null(不为空)
数据库默认字段基本都是字段为空,但是实际开发时,尽可能保证字段不为空,因为数据为空没办法参与运算
案例:
创建一个班级表,包含班级名和所在的教室。
如果班级没有名字,就不知道在哪个班级
如果教室名字为空,就不知道在哪上课
所以对于班级和教室列,其不能为空
mysql> create table tt1(class_id int not null,classroom varchar(10) not null);
Query OK, 0 rows affected (0.08 sec)
mysql> desc tt1;
+-----------+-------------+------+-----+---------+-------+
| Field | Type | Null | Key | Default | Extra |
+-----------+-------------+------+-----+---------+-------+
| class_id | int | NO | | NULL | |
| classroom | varchar(10) | NO | | NULL | |
+-----------+-------------+------+-----+---------+-------+
2 rows in set (0.00 sec)
mysql> insert into tt1 value(1,'行远楼');
Query OK, 1 row affected (0.02 sec)
mysql> insert into tt1 value(1);
ERROR 1136 (21S01): Column count doesn't match value count at row 1
二、默认值
默认值:某一种数据会经常性的出现某个具体的值,可以一开始就指定好,在需要真实数据的时候,用户可选择性的使用默认值。
mysql> alter table tt1 add column lesson char(4) default '自习';
Query OK, 0 rows affected (0.05 sec)
Records: 0 Duplicates: 0 Warnings: 0
mysql> desc tt1;
+-----------+-------------+------+-----+---------+-------+
| Field | Type | Null | Key | Default | Extra |
+-----------+-------------+------+-----+---------+-------+
| class_id | int | NO | | NULL | |
| classroom | varchar(10) | NO | | NULL | |
| lesson | char(4) | YES | | 自习 | |
+-----------+-------------+------+-----+---------+-------+
3 rows in set (0.00 sec)
mysql> select * from tt1;
+----------+-----------+--------+
| class_id | classroom | lesson |
+----------+-----------+--------+
| 1 | 行远楼 | 自习 |
+----------+-----------+--------+
1 row in set (0.00 sec)
三、列描述
列描述:comment,没有实际含义,专门用来描述字段,类似于列的注释
mysql> alter table tt1 add column teacher char(5) default '无' comment '老师';
Query OK, 0 rows affected (0.06 sec)
Records: 0 Duplicates: 0 Warnings: 0
mysql> desc tt1;
+-----------+-------------+------+-----+---------+-------+
| Field | Type | Null | Key | Default | Extra |
+-----------+-------------+------+-----+---------+-------+
| class_id | int | NO | | NULL | |
| classroom | varchar(10) | NO | | NULL | |
| lesson | char(4) | YES | | 自习 | |
| teacher | char(5) | YES | | 无 | |
+-----------+-------------+------+-----+---------+-------+
4 rows in set (0.00 sec)
通过desc是查看不到注释信息的,得通过show
mysql> show create table tt1\G
*************************** 1. row ***************************
Table: tt1
Create Table: CREATE TABLE `tt1` (
`class_id` int NOT NULL,
`classroom` varchar(10) NOT NULL,
`lesson` char(4) DEFAULT '自习',
`teacher` char(5) DEFAULT '无' COMMENT '老师'
) ENGINE=InnoDB DEFAULT CHARSET=utf8mb4 COLLATE=utf8mb4_0900_ai_ci
1 row in
四、主键
主键:primary key用来唯一的约束该字段里面的数据,不能重复,不能为空,一张表中最多只能有一个主键,主键所在的列通常是整数类型。
案例:
创建表的时候直接在字段上指定主键
mysql> create table tt2(id int unsigned primary key comment '学号不能为空',
-> name varchar(20) not null);
Query OK, 0 rows affected (0.07 sec)
mysql> desc tt2;
+-------+--------------+------+-----+---------+-------+
| Field | Type | Null | Key | Default | Extra |
+-------+--------------+------+-----+---------+-------+
| id | int unsigned | NO | PRI | NULL | |
| name | varchar(20) | NO | | NULL | |
+-------+--------------+------+-----+---------+-------+
2 rows in set (0.00 sec)
mysql> insert into tt2 value(1,'张三');
Query OK, 1 row affected (0.02 sec)
mysql> insert into tt2(name) value('张三');
ERROR 1364 (HY000): Field 'id' doesn't have a default value
mysql> insert into tt2 value(1,'张三');
ERROR 1062 (23000): Duplicate entry '1' for key 'tt2.PRIMARY'
删除主键&&追加主键
mysql> alter table tt2 drop primary key;
Query OK, 1 row affected (0.18 sec)
Records: 1 Duplicates: 0 Warnings: 0
mysql> desc tt2;
+-------+--------------+------+-----+---------+-------+
| Field | Type | Null | Key | Default | Extra |
+-------+--------------+------+-----+---------+-------+
| id | int unsigned | NO | | NULL | |
| name | varchar(20) | NO | | NULL | |
+-------+--------------+------+-----+---------+-------+
2 rows in set (0.00 sec)
mysql> alter table tt2 add primary key(id);
Query OK, 0 rows affected (0.16 sec)
Records: 0 Duplicates: 0 Warnings: 0
mysql> desc tt2;
+-------+--------------+------+-----+---------+-------+
| Field | Type | Null | Key | Default | Extra |
+-------+--------------+------+-----+---------+-------+
| id | int unsigned | NO | PRI | NULL | |
| name | varchar(20) | NO | | NULL | |
+-------+--------------+------+-----+---------+-------+
2 rows in set (0.00 sec)
复合主键
创建表的时候,在所有字段以后,使用primary key(主键字段列表)来创建主键,如果有多个字段作为主键,可以使用复合主键。
mysql> create table tt3( id int unsigned, course char(10) ,score tinyint unsigned default 60 , primary key (id,course));
Query OK, 0 rows affected (0.20 sec)
mysql> desc tt3;
+--------+------------------+------+-----+---------+-------+
| Field | Type | Null | Key | Default | Extra |
+--------+------------------+------+-----+---------+-------+
| id | int unsigned | NO | PRI | NULL | |
| course | char(10) | NO | PRI | NULL | |
| score | tinyint unsigned | YES | | 60 | |
+--------+------------------+------+-----+---------+-------+
3 rows in set (0.00 sec)
mysql> insert into tt3 value(1,'高数',40);
Query OK, 1 row affected (0.05 sec)
mysql> insert into tt3 value(1,'大物',40);
Query OK, 1 row affected (0.01 sec)
mysql> insert into tt3 value(1,'高数',40);
ERROR 1062 (23000): Duplicate entry '1-高数' for key 'tt3.PRIMARY'
五、自增长
auto_increment:当对应的字段,不给值,会自动的被系统触发,系统会从当前字段中已经有的最大值+1操作,得到一个新的不同的值。通常会搭配主键一起使用,作为逻辑主键
自增长的特点:
- 任何一个字段要做自增长,前提是本身是一个索引(key一栏有值)
- 自增长字段必须是整数
- 一张表最多只能有一个自增长
mysql> create table tt4(
-> id int unsigned primary key auto_increment,
-> name varchar(10) not null default ''
-> );
Query OK, 0 rows affected (0.09 sec)
mysql> insert into tt4(name) value('a');
Query OK, 1 row affected (0.02 sec)
mysql> insert into tt4(name) value('b');
Query OK, 1 row affected (0.02 sec)
mysql> select * from tt4;
+----+------+
| id | name |
+----+------+
| 1 | a |
| 2 | b |
+----+------+
2 rows in set (0.00 sec)
索引:
数据库索引是一种用于提高数据查询效率的数据结构,可以把它理解为书籍的目录。没有索引时,数据库可能需要逐行扫描整张表,才能找到符合条件的数据;建立索引后,数据库可以利用索引结构快速定位目标记录,减少需要扫描的数据量。以 MySQL 的 InnoDB 引擎为例,常见索引采用 B+ 树组织数据,主键索引的叶子节点存储完整的行数据,二级索引的叶子节点存储索引列的值和对应的主键值。当查询的列没有合适的索引时,数据库通常需要全表扫描;但即使存在索引,MySQL 优化器也会根据查询条件和成本决定是否使用索引。需要注意,索引能够提高查询效率,但也会占用额外的存储空间,并增加插入、删除和更新数据时维护索引的开销。
六、唯一键
一张表中往往有很多字段需要唯一性,数据不能重复,但是一张表中只能有一个主键:唯一键就可以解决表中有多个字段需要唯一性约束的问题。
唯一键的本质和主键差不多,唯一键允许为空,而且可以多个位空,空字符不做唯一性比较。
-
主键: 每条记录必须有一个稳定、唯一的标识。
-
唯一键: 某个业务字段确实不允许重复时,使用唯一约束保证数据正确性。
例:
mysql> create table tt5(
-> id char(10) unique ,
-> name varchar(10)
-> );
Query OK, 0 rows affected (0.10 sec)
mysql> insert into tt5 values('01','aaa');
Query OK, 1 row affected (0.03 sec)
mysql> insert into tt5 values('02','aaa');
Query OK, 1 row affected (0.02 sec)
mysql> insert into tt5 values('01','bbb');
ERROR 1062 (23000): Duplicate entry '01' for key 'tt5.id'
七、外键
外键用于定义主表和从表之间的关系:外键约束主要定义在从表上,主表则必须是有主键约束或者unique约束。当定义外键后,要求外键列数据必须在主表的主键列存在或为null
语法:
foreign key (字段名)references 主表(列)
案例:

mysql> create table myclass(
-> id int,
-> name varchar(30) not null comment '班级名',
-> primary key(id)
-> );
Query OK, 0 rows affected (0.09 sec)
mysql> create table stu(
-> id int primary key,
-> name varchar(30) not null comment '学生名',
-> class_id int,
-> foreign key(class_id) references myclass(id)
-> );
插入两个班级
mysql> insert into myclass value(1,'2401');
Query OK, 1 row affected (0.01 sec)
mysql> insert into myclass value(2,'2402');
Query OK, 1 row affected (0.02 sec)
插入两个学生
mysql> insert into stu value(1,'wtyh',1);
Query OK, 1 row affected (0.03 sec)
mysql> insert into stu value(2,'djh',2);
Query OK, 1 row affected (0.01 sec)
插入第三个学生,由于主表无该班级,所以插入失败
mysql> insert into stu value(3,'whx',3);
ERROR 1452 (23000): Cannot add or update a child row: a foreign key constraint fails (`school_2`.`stu`, CONSTRAINT `stu_ibfk_1` FOREIGN KEY (`class_id`) REFERENCES `myclass` (`id`))
如何理解外键约束
外键约束用于维护关联表之间的引用完整性。例如,学生表中的 class_id 引用班级表的 id,那么学生所属的班级必须存在。MySQL 会在插入、更新或删除相关数据时检查外键约束,防止出现无效的关联关系。