MySQL通过外键约束实现数据库的参照完整性,外键约束条件可在创建外键时指定,table的存储引擎只能是InnoDB,因为只有这种存储模式才支持外键。

外键约束条件有以下4种:

(1)restrict方式:同no action,都是立即检查外键约束;

- - 限制,指的是如果子表引用父表的某个字段的值,那么不允许直接删除父表的该值。

(2)cascade方式:在父表上update/delete记录时,同步update/delete子表的匹配记录 ;

On delete cascade从mysql3.23.50开始可用,on update cascade从mysql4.0.8开始可用 ;

-- 级联,删除/更新父表的某条记录,子表中引用该值的记录会自动被删除/更新。

(3)No action方式:如果子表中有匹配的记录,则不允许对父表对应候选键进行update/delete操作 这个是ANSI SQL-92标准,从mysql4.0.8开始支持;

--无参照完整性关系,有了也不生效。

(4)set null方式:在父表上update/delete记录时,将子表上匹配记录的列设为null 要注意子表的外键列不能为not null

On delete set null从mysql3.23.50开始可用;,on update set null从mysql4.0.8开始可用 。

首先创建一个用户表,并插入两条记录:

mysql> create table t_group-> (id int auto_increment primary key,-> name varchar(20))-> engine=InnoDB;
Query OK, 0 rows affected (0.08 sec)mysql> insert into t_group values (1,'Group_1'),(2,'Group_2');
Query OK, 2 rows affected (0.04 sec)
Records: 2  Duplicates: 0  Warnings: 0mysql> select * from t_group;
+----+---------+
| id | name    |
+----+---------+
|  1 | Group_1 |
|  2 | Group_2 |
+----+---------+
2 rows in set (0.00 sec)

1.级联方式

创建级联子表:

mysql> create table t_user-> (id int not null primary key,-> name varchar(10),groupid int,-> foreign key(groupid) references t_group(id)-> on delete cascade on update cascade)-> engine=InnoDB;
Query OK, 0 rows affected (0.08 sec)

完整性约束测试,以下例子都省略完整性测试:

mysql> insert into t_user values (1,'dayu',1),(2,'duoduo',2);
Query OK, 2 rows affected (0.08 sec)
Records: 2  Duplicates: 0  Warnings: 0mysql> insert into t_user values (1,'huanhuan',1);   //实体完整性测试,不能插入重复主键值
ERROR 1062 (23000): Duplicate entry '1' for key 'PRIMARY'
mysql> insert into t_user values (3,'maiqi',3);      //参照完整性测试,不能插入在主表中不存在的外键值
ERROR 1452 (23000): Cannot add or update a child row: a foreign key constraint fails (`test`.`t_user`, CONSTRAINT `t_user_ibfk_1` FOREIGN KEY (`groupid`) REFERENCES `t_group` (`id`) ON DELETE CASCADE ON UPDATE CASCADE)

级联测试:

mysql> select * from t_user;
+----+--------+---------+
| id | name   | groupid |
+----+--------+---------+
|  1 | dayu   |       1 |
|  2 | duoduo |       2 |
+----+--------+---------+
2 rows in set (0.00 sec)mysql> update t_group set id=3 where id=2;  //从主表中更新一个记录
Query OK, 1 row affected (0.02 sec)
Rows matched: 1  Changed: 1  Warnings: 0mysql> select * from t_user;  /改变主表数据,从表数据随着更新
+----+--------+---------+
| id | name   | groupid |
+----+--------+---------+
|  1 | dayu   |       1 |
|  2 | duoduo |       3 |
+----+--------+---------+
2 rows in set (0.00 sec)

  

mysql> select * from t_user;
+----+--------+---------+
| id | name   | groupid |
+----+--------+---------+
|  1 | dayu   |       1 |
|  2 | duoduo |       3 |
+----+--------+---------+
2 rows in set (0.00 sec)mysql> delete from t_group where id=3;  //从主表中删除一个记录
Query OK, 1 row affected (0.03 sec)mysql> select * from t_user;   //子表中对应的记录自动被删除
+----+------+---------+
| id | name | groupid |
+----+------+---------+
|  1 | dayu |       1 |
+----+------+---------+
1 row in set (0.00 sec)

  

2.置空模式(set null,主表记录被删除,从表中对应的值设置为NULL)

首先创建一个子表:

 mysql> select * from t_group;
 +----+---------+
 | id | name |
 +----+---------+
 | 1 | Group_1 |
 | 2 | Group_2 |
 +----+---------+
 2 rows in set (0.00 sec)

mysql> create table t_user_1-> (id int not null primary key,-> name char(10),groupid int,-> foreign key(groupid) references t_group(id)-> on delete set null on update set null)-> engine=InnoDB;
Query OK, 0 rows affected (0.11 sec)mysql> insert into t_user_1 values (1,'dayu',1),(2,'duoduo',2),(3,'huanhuan',2),(4,'maiqi',1);
Query OK, 4 rows affected (0.02 sec)
Records: 4  Duplicates: 0  Warnings: 0mysql> select * from t_user_1;
+----+----------+---------+
| id | name     | groupid |
+----+----------+---------+
|  1 | dayu     |       1 |
|  2 | duoduo   |       2 |
|  3 | huanhuan |       2 |
|  4 | maiqi    |       1 |
+----+----------+---------+
4 rows in set (0.00 sec)

mysql> update t_group set id=3 where id=1;
Query OK, 1 row affected (0.03 sec)
Rows matched: 1  Changed: 1  Warnings: 0mysql> select * from t_user_1;
+----+----------+---------+
| id | name     | groupid |
+----+----------+---------+
|  1 | dayu     |    NULL |
|  2 | duoduo   |       2 |
|  3 | huanhuan |       2 |
|  4 | maiqi    |    NULL |
+----+----------+---------+
4 rows in set (0.00 sec)mysql> delete from t_group where id=2;   //从主表中删除一个记录
Query OK, 1 row affected (0.01 sec)mysql> select * from t_user_1;  //子表中对应的属性值被自动设置为NULL
+----+----------+---------+
| id | name     | groupid |
+----+----------+---------+
|  1 | dayu     |    NULL |
|  2 | duoduo   |    NULL |
|  3 | huanhuan |    NULL |
|  4 | maiqi    |    NULL |
+----+----------+---------+
4 rows in set (0.00 sec)

3.禁止模式(no action/restrict),如果在子表中有引用,则不允许在主表中进行更新或删除

首先创建一个子表:

mysql> select * from t_group;+----+---------+| id | name |+----+---------+| 1 | Group_1 || 2 | Group_2 |+----+---------+2 rows in set (0.00 sec)mysql> create table t_user_2-> (id int not null primary key,-> name char(10),groupid int,-> foreign key(groupid) references t_group(id)-> on delete no action on update restrict)-> engine=InnoDB;
Query OK, 0 rows affected (0.11 sec)mysql> insert into t_user_2 values (1,'dayu',1),(2,'duoduo',2),(3,'huanhuan',2),(4,'maiqi',1);
Query OK, 4 rows affected (0.02 sec)
Records: 4  Duplicates: 0  Warnings: 0mysql> select * from t_user_2;
+----+----------+---------+
| id | name     | groupid |
+----+----------+---------+
|  1 | dayu     |       1 |
|  2 | duoduo   |       2 |
|  3 | huanhuan |       2 |
|  4 | maiqi    |       1 |
+----+----------+---------+
4 rows in set (0.00 sec)

mysql> update t_group set id=3 where id=1;
ERROR 1451 (23000): Cannot delete or update a parent row: a foreign key constraint fails (`test`.`t_user_2`, CONSTRAINT `t_user_2_ibfk_1` FOREIGN KEY (`groupid`) REFERENCES `t_group` (`id`) ON DELETE NO ACTION)
mysql> delete from t_group where id=2;
ERROR 1451 (23000): Cannot delete or update a parent row: a foreign key constraint fails (`test`.`t_user_2`, CONSTRAINT `t_user_2_ibfk_1` FOREIGN KEY (`groupid`) REFERENCES `t_group` (`id`) ON DELETE NO ACTION)

4.主从表的删除

删除从表没有限制,如下:

mysql> drop table t_user_2;
Query OK, 0 rows affected (0.01 sec)

如果存在引用的从表,则主要不能随意删除:

mysql> drop table t_group;
ERROR 1217 (23000): Cannot delete or update a parent row: a foreign key constraint fails

经过以上测试,了解到MySQL通过外键约束实现了数据的完整性与一致性。

转载于:https://www.cnblogs.com/yy20141204bb/p/8405000.html

MySQL外键约束_ON DELETE CASCADE/ON UPDATE CASCADE相关推荐

  1. MySQL外键约束On Delete、On Update各取值的含义

    主键.外键和索引的区别?   主键 外键 索引 定义: 唯一标识一条记录,不能有重复的,不允许为空 表的外键是另一表的主键, 外键可以有重复的, 可以是空值 主索引(由关键字PRIMARY定义的索引) ...

  2. mysql on delete关键字_MySQL外键约束On Delete、On Update各取值的含义

    主键.外键和索引的区别? 主键 外键 索引 定义: 唯一标识一条记录,不能有重复的,不允许为空 表的外键是另一表的主键,外键可以有重复的,可以是空值 主索引(由关键字PRIMARY定义的索引),用于表 ...

  3. mysql on cascade_MySQL外键约束_ON DELETE CASCADE/ON UPDATE CASCADE

    MySQL通过外键约束实现数据库的参照完整性,外键约束条件可在创建外键时指定,table的存储引擎只能是InnoDB,因为只有这种存储模式才支持外键. 外键约束条件有以下4种: (1)restrict ...

  4. mysql外键约束脚本_如何在MySQL中设置外键约束

    (1) 外键的使用: 外键的作用,主要有两个: 一个是让数据库自己通过外键来保证数据的完整性和一致性 一个就是能够增加ER图的可读性 有些人认为外键的建立会给开发时操作数据库带来很大的麻烦.因为数据库 ...

  5. mysql外键约束语句级连_mysql之外键约束(级联操作等) 父表子表

    不理解的地方标注问号. 网上不同的博客讲的,之间似乎有些矛盾,求推荐好书. 写得不好请指出错误. 父表和子表 当两个表建立一对多关系的时候,"一"的那一端是父表,"多&q ...

  6. MySQL——外键约束

    设置外键约束(FOREIGN KEY, FK ) MySQL外键约束是表的一个特殊字段,经常与外键约束一起使用.对于两个具有关联关系的表而言,相关字段中主键所在表称为主表(父表),外键所在表称为从表( ...

  7. mysql外键约束详解_详解MySQL 外键约束

    详解MySQL 外键约束,西欧,西西里,玛雅,兵种,诺曼 详解MySQL 外键约束 易采站长站,站长之家为您整理了详解MySQL 外键约束的相关内容. 官方文档: https://dev.mysql. ...

  8. mysql外键约束的作用_MySql外键约束作用

    NO ACTION 指定如果试图删除/修改某一行,而该行的键被其他表的现有行中的外键所引用,则产生错误并回滚 DELETE/UPDATE语句. CASCADE.SET NULL 和 SET DEFAU ...

  9. mysql 外键约束_MySQL之外键约束(FOREIGN KEY)

    定义: MySQL外键约束(FOREIGN KEY)用来在两个表的数据之间建立链接,它可以是一列或者多列.一个表可以有一个或多个外键. 外键对应的是参照完整性,一个表的外键可以为空值,若不为空值,则每 ...

最新文章

  1. 我和美国 AI 博士聊了聊:2020 年,这件事比存钱更重要!
  2. 【leetcode】Best Time to Buy and Sell Stock
  3. Azure Automation (5) 调整Azure SQL Database DTU
  4. Leaflet中使用Leaflet.Path.Transform插件实现旋转图形
  5. OpenGL:纹理Textures
  6. mysql 5.6.14 win32_mysql-5.6.14-win32为免安装解压缩版
  7. php 删除%3ca%3e标签,a和table标签的应用
  8. 云计算99.9%可用性毫无意义 灾难恢复是关键
  9. Joe Hocking - Unity in Action. 2nd Ed [2018]
  10. 用系统自带的SSH实现两台linux密钥认证访问
  11. 程序运行产生SIGABRT信号的原因
  12. unity代码控制物体的透明度总结
  13. WZOI-359字符串哈希
  14. php日志分析,PHP SeasLog实现高性能日志记录
  15. 基于C#开发(WinForm)排队叫号系统【100010339】
  16. 第三章 part2 单调性与极值
  17. 元宇宙+DAO=ZOO-Crypto World
  18. 产品读书《用户界面设计-有效的人机交互策略》
  19. 沈师附属艺术学校计算机,沈阳师范大学附属学校(沈师附中)基本情况介绍
  20. 高项论文练习--项目进度管理

热门文章

  1. python后端设计_Python后端设计模式
  2. monggodb和MySQL同步问题_monggoDB添加到windows服务
  3. Spark集群资源如何分配
  4. R语言︱缺失值处理之多重插补——mice包
  5. 表格开源的数据集FUSD数据集、TableBank数据集、DocBank数据集
  6. 静态成员常量的初始化
  7. module.exports与exports,export与export defa
  8. spring jdbcTemplate中获取jdbc Connection并执行操作
  9. 阿里云虚拟主机的使用,附幸运券领取
  10. 浅谈php之设计模式基础