【表的完整性约束&外键约束】

外键约束

今天跟大家聊聊这个外键约束,简单来说呢,就是,嗯,,关于两个表的操作。对,就是这样的,来跟我一起看看叭。
【1】什么是外键约束?
外键约束(FOREIGN KEY,缩写FK)是用来实现数据库表的参照完整性的。外键约束可以使两张表紧密的结合起来,特别是针对修改或者删除的级联操作时,会保证数据的完整性。
外键是指表中某个字段的值依赖于另一张表中某个字段的值,而被依赖的字段必须具有主键约束或者唯一约束。被依赖的表我们通常称之为父表或者主表,设置外键约束的表称为子表或者从表。

举个例子:如果想要表示学生和班级的关系,首先要有学生表和班级表两张表,然后学生表中有个字段为stu_clazz(该字段表示学生所在的班级),而该字段的取值范围由班级表中的主键cla_no字段(该字段表示班级编号)的取值决定。那么班级表为主表,学生表为从表,且stu_clazz字段是学生表的外键。通过stu_clazz字段就建立了学生表和班级表的关系。
在这里插入图片描述
主表(父表):班级表 - 班级编号 - 主键
从表(子表):学生表 - 班级编号 - 外键

【2】sql展示:

-- 先创建父表:班级表:
create table t_class(
        cno int(4) primary key auto_increment,
        cname varchar(10) not null,
        room char(4)
)
-- 添加班级数据:
insert into t_class values (null,'java001','r803');
insert into t_class values (null,'java002','r416');
insert into t_class values (null,'大数据001','r103');
-- 可以一次性添加多条记录:
insert into t_class values (null,'java001','r803'),(null,'java002','r416'),(null,'大数据001','r103');
-- 查询班级表:
select * from t_class;
-- 学生表删除:
drop table t_student;
-- 创建子表,学生表:
create table t_student(
        sno int(6) primary key auto_increment, 
        sname varchar(5) not null, 
        classno int(4)  -- 取值参考t_class表中的cno字段,不要求字段名字完全重复,但是类型长度定义 尽量要求相同。
);
-- 添加学生信息:
insert into t_student values (null,'张三',1),(null,'李四',1),(null,'王五',2);
-- 查看学生表:
select * from t_student;
-- 出现问题:
-- 1.添加一个学生对应的班级编码为4:
insert into t_student values (null,'丽丽',4);
-- 2.删除班级2:
delete from t_class where cno = 2;
-- 出现问题的原因:
-- 因为你现在的外键约束,没用语法添加进去,现在只是逻辑上认为班级编号是外键,没有从语法上定义
-- 解决办法,添加外键约束:
-- 注意:外键约束只有表级约束,没有列级约束:
create table t_student(
        sno int(6) primary key auto_increment, 
        sname varchar(5) not null, 
        classno int(4),-- 取值参考t_class表中的cno字段,不要求字段名字完全重复,但是类型长度定义 尽量要求相同。
                                constraint fk_stu_classno foreign key (classno) references t_class (cno)
);
create table t_student(
        sno int(6) primary key auto_increment, 
        sname varchar(5) not null, 
        classno int(4)
);
-- 在创建表以后添加外键约束:
alter table t_student add constraint fk_stu_classno foreign key (classno) references t_class (cno)
-- 上面的两个问题都解决了:
-- 添加学生信息:
-- > 1452 - Cannot add or update a child row: a foreign key constraint fails (`mytestdb`.`t_student`, CONSTRAINT `fk_stu_classno` FOREIGN KEY (`classno`) REFERENCES `t_class` (`cno`))
insert into t_student values (null,'张三',1),(null,'李四',1),(null,'王五',2);
-- 删除班级1-- 2.删除班级2:
insert into t_student values (null,'张三',3),(null,'李四',3),(null,'王五',3);
-- > 1451 - Cannot delete or update a parent row: a foreign key constraint fails (`mytestdb`.`t_student`, CONSTRAINT `fk_stu_classno` FOREIGN KEY (`classno`) REFERENCES `t_class` (`cno`))
delete from t_class where cno = 3;

外键策略

外键策略呢,是根据两表之间所需要的操作通过四个外键策略来实现。

-- 学生表删除:
drop table t_student;
-- 班级表删除:
drop table t_class;
-- 注意:先删除从表,再删除主表。
-- 先创建父表:班级表:
create table t_class(
        cno int(4) primary key auto_increment,
        cname varchar(10) not null,
        room char(4)
)
-- 可以一次性添加多条记录:
insert into t_class values (null,'java001','r803'),(null,'java002','r416'),(null,'大数据001','r103');
-- 添加学生表,添加外键约束:
create table t_student(
        sno int(6) primary key auto_increment, 
        sname varchar(5) not null, 
        classno int(4),-- 取值参考t_class表中的cno字段,不要求字段名字完全重复,但是类型长度定义 尽量要求相同。
                                constraint fk_stu_classno foreign key (classno) references t_class (cno)
);
-- 可以一次性添加多条记录:
insert into t_student values (null,'张三',1),(null,'李四',1),(null,'王五',2),(null,'朱六',3);
-- 查看班级表和学生表:
select * from t_class;
select * from t_student;
-- 删除班级2:如果直接删除的话肯定不行因为有外键约束:
-- 加入外键策略:
-- 策略1:no action 不允许操作
-- 通过操作sql来完成:
-- 先把班级2的学生对应的班级 改为null 
update t_student set classno = null where classno = 2;
-- 然后再删除班级2:
delete from t_class where cno = 2;
-- 策略2:cascade 级联操作:操作主表的时候影响从表的外键信息:
-- 先删除之前的外键约束:
alter table t_student drop foreign key fk_stu_classno;
-- 重新添加外键约束:
alter table t_student add constraint fk_stu_classno foreign key (classno) references t_class (cno) on update cascade on delete cascade;
-- 试试更新:
update t_class set cno = 5 where cno = 3;
-- 试试删除:
delete from t_class where cno = 5;
-- 策略3set null  置空操作:
-- 先删除之前的外键约束:
alter table t_student drop foreign key fk_stu_classno;
-- 重新添加外键约束:
alter table t_student add constraint fk_stu_classno foreign key (classno) references t_class (cno) on update set null on delete set null;
-- 试试更新:
update t_class set cno = 8 where cno = 1;
-- 注意:
-- 1. 策略2 级联操作  和  策略2 的  删除操作  可以混着使用:
alter table t_student add constraint fk_stu_classno foreign key (classno) references t_class (cno) on update cascade on delete set null ;
-- 2.应用场合:
--1)朋友圈删除,点赞。留言都删除  --  级联操作
--2)解散班级,对应的学生 置为班级为null就可以了,-- set null

我只想卷死自己,或者被自己卷死!!!
在这里插入图片描述

  • 1
    点赞
  • 7
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 1
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

言chengxu

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值