day36_8_20数据库3外键
一。一对多
在数据库使用数据中经常遇到一对多的情况,以公司员工为例。
一张完整的员工表有以下字段:
id name gender dep_name dep_desc .
以此建表得:
- id name gender dep_name dep_desc
- 1 jason male 教学部 教书育人
- 2 egon male 外交部 漂泊游荡
- 3 tank male 教学部 教书育人
- 4 kevin male 教学部 教书育人
- 5 owen female 技术部 技术能力有限部门
少数的数据看不出有多大的不合理,但是如果一个公司中频繁有教学部的出现,它和它的描述就要反复写一遍,这种感觉就像一个py文件写下了所有的代码,这本身就是不合理的,为了像模块一样封装代码,我们先将其分成2个表,再使用一对多的关系关联两表:
- emp:
- id name gender dep_id
- 1 jason male 1
- 2 egon male 2
- 3 tank male 2
- 4 kevin male 2
- 5 owen female 3
- dep
- id dep_name dep_desc
- 1 教学部 教书育人
- 2 外交部 漂泊游荡
- 3 教学部 教书育人
- 4 教学部 教书育人
- 5 技术部 技术能力有限部门
两张表唯一有关系的是dep_id,所以要将dep_id设置成外键。
设置外键是在表的创建阶段就完成的工作,一般的,我们把外键设置在一对多的多那个表中:
- create table dep(
- id int primary key auto_increment,
- dep_name char(10),
- dep_comment char(60)
- );
- create table emp(
- id int primary key auto_increment,
- name char(16),
- gender enum('male','female') not null default 'male',
- dep_id int,
- foreign key(dep_id) references dep(id)
- );
在插入记录时,必须先插入被关联的表,也就是dep,在插入emp的数据。
这样的表当dep中 的数据emp使用时,它的数据是不能被删除的,为了使得两者具有同步性,使用on delete cascade 修饰外键:
- create table dep(
- id int primary key auto_increment,
- dep_name char(10),
- dep_comment char(60)
- );
- create table emp(
- id int primary key auto_increment,
- name char(16),
- gender enum('male','female') not null default 'male',
- dep_id int,
- foreign key(dep_id) references dep(id)
- on update cascade
- on delete cascade
- );
如图:
二。多对多
除了一对多的概念以外,还有多对多,如图书和作者的关系。
一个作者可以发布多个书。
一个书可以有多个作者。
于是根据上述的1对多推理出可以这样建立:
- create table book(
- id int primary key auto_increment,
- title varchar(32),
- price int,
- author_id int,
- foreign key(author_id) references author(id)
- on update cascade # 同步更新
- on delete cascade # 同步删除
- );
- create table author(
- id int primary key auto_increment,
- name varchar(32),
- age int,
- book_id int,
- foreign key(book_id) references book(id)
- on update cascade # 同步更新
- on delete cascade # 同步删除
- );
结果肯定是错的,建表book是让关联author,建表author时让关联book,两个谁都不能先建立肯定时不行的。
所以需要第三张表,来记录它们之间的关系。
- create table book(
- id int primary key auto_increment,
- title varchar(32),
- price int
- );
- create table author(
- id int primary key auto_increment,
- name varchar(32),
- age int
- );
- create table book2author(
- id int primary key auto_increment,
- book_id int,
- foreign key(book_id) references book(id)
- on update cascade
- on delete cascade,
- author_id int,
- foreign key(author_id) references author(id)
- on update cascade
- on delete cascade
- );
如图:
三。一对一
一对一的使用场景是当数据库特别庞大时,可以考虑分表。
分表后使用一对一的关系将其连接起来。
首先先建立被关联的表,再建立关联表,外键可以设置再任何地方,但一般设置在访问比较的的那个表。
- create table authordetail1(
- id int primary key auto_increment,
- phone int,
- addr char(255)
- );
- create table author1(
- id int primary key auto_increment,
- name char(4),
- age int,
- authordetail_id int unique,
- foreign key(authordetail_id) references authordetail1(id)
- on update cascade
- on delete cascade
- );
四,表修改
- # mysql对大小写不敏感!!!
- 语法:
- 1. 修改表名
- ALTER TABLE 表名
- RENAME 新表名;
- 2. 增加字段
- ALTER TABLE 表名
- ADD 字段名 数据类型 [完整性约束条件…],
- ADD 字段名 数据类型 [完整性约束条件…];
- ALTER TABLE 表名
- ADD 字段名 数据类型 [完整性约束条件…] FIRST;
- ALTER TABLE 表名
- ADD 字段名 数据类型 [完整性约束条件…] AFTER 字段名;
- 3. 删除字段
- ALTER TABLE 表名
- DROP 字段名;
- 4. 修改字段 # modify只能改字段数据类型完整约束,不能改字段名,但是change可以!
- ALTER TABLE 表名
- MODIFY 字段名 数据类型 [完整性约束条件…];
- ALTER TABLE 表名
- CHANGE 旧字段名 新字段名 旧数据类型 [完整性约束条件…];
- ALTER TABLE 表名
- CHANGE 旧字段名 新字段名 新数据类型 [完整性约束条件…];
五。表复制
- # 查询语句执行的结果也是一张表,可以看成虚拟表
- # 复制表结构+记录 (key不会复制: 主键、外键和索引)
- create table new_service select * from service;
- # 只复制表结构
- select * from service where 1=2; //条件为假,查不到任何记录
- create table new1_service select * from service where 1=2;
- create table t4 like employees;
day36_8_20数据库3外键的更多相关文章
- MySQL数据库建立外键失败的原因总结
在MySQL数据库创建外键时,经常会发生一些错误,这是一件很令人头疼的事.一个典型的错误就是:Can’t create table... 的错误.在很多实例中,这种错误的发生都是因为mysql一直以来 ...
- MySQL数据库有外键约束时使用truncate命令的办法
MySQL数据库操作中,Delete与Truncate两个命令都可以删除一个数据表中的全部数据,使用办法分别是: DELETE FROM t_question TRUNCATE TABLE t_que ...
- 使用Navicat V8.0创建数据库,外键出现错误ERROR 1005: Can’t create table (errno: 121)
ERROR 1005: Can't create table (errno: 121) errno 121 means a duplicate key error. Probably the tabl ...
- mysql数据库导入外键约束问题
在网站搬迁过程中,很重要一点是数据的迁移.你的数据库可能已经包含了一个设计良好的数据表集合,并且在网站运营过程中,产生了重要的数据.这时你必须做好包含数据表schema以及数据本身的迁移. 完成上述数 ...
- 数据库 SQL 外键约束 多表查询
多表设计与多表查询 1.外键约束 表是用来保存现实生活中的数据的,而现实生活中数据和数据之间往往具有一定的关系,我们在使用表来存储数据时,可以明确的声明表和表之前的依赖关系,命令数据库来 ...
- 详解MariaDB数据库的外键约束
1.什么是外键约束 外键约束(foreign key)就是表与表之间的某种约定的关系,由于这种关系的存在,我们能够让表与表之间的数据,更加的完整,关连性更强. 关于数据表的完整性和关连性,可以举个例子 ...
- django2.0变动数据库设置外键报错
1.报错TypeError: __init__() missing 1 required positional argument: 'on_delete' django2.0以后创建数据库外键的时候必 ...
- flask对数据库的外键 主键
近期一直在学flask框架,后悔当初没有好好学习数据库.一个外键的知识,真的是太....蓝瘦香菇 创建数据库 class Users(db.Model): __tablename__ = 'users ...
- sql 删除数据库表 外键
--/第1步**********删除所有表的外键约束*************************/ DECLARE c1 cursor for select 'alter table ['+ ...
随机推荐
- jdbc工具类是多例的
一直以为他 是单例的, 以为创建个工具类就是为了单例, 节省效率 , 其实 是为了封装代码, 简洁 ! 还有重要一点 : 所欲工具类里面不要抛异常 要捕捉异常 !
- 【正则】day01
正则表达式一.概述 验证 网络爬虫. 概念: 具有语法格式的字符串. 函数 PCRE 1.perl语言正则语法兼容.(java c) 2.速度快,效率高. P ...
- hex2pcap
#include <stdlib.h> #include <stdio.h> #include <string.h> typedef struct { unsign ...
- 软件工程实践2019——idea表述及组队
时间:2019-10-08 随堂 欢迎每个有想法的同学都积极参与idea表述,用心呈现你的心中所想.你心中热爱的,希望在软工实践项目中完成的项目作品.每个愿意表达idea的同学,都有一分钟时间来呈现作 ...
- es6中reduce()方法和reduceRight()方法
es6中reduce()方法从左往右开始 参数:prev:它是上一次调用回调时返回的结果,每次调用的结果都会给prev cur:当前的元素 index:当前的索引 arr:循环的数组 返回值:函数累计 ...
- mysql增加索引、删除索引、查看索引
添加索引 有四种方式来添加数据表的索引: 1.添加一个主键,这意味着索引值必须是唯一的,且不能为NULL ALTER TABLE tbl_name ADD PRIMARY KEY (column_li ...
- SpringBoot2版本Caused by: java.sql.SQLSyntaxErrorException: Table 'dinner.hibernate_sequenc
1.SpringBoot2版本Caused by: java.sql.SQLSyntaxErrorException: Table 'dinner.hibernate_sequenc报错. -java ...
- c# Equal函数 and 运算符'==' (原发布 csdn 2017年10月15日 20:39:26)
1.==.!=.<.>.<= 和>= 运算符为比较运算符(comparison operator).C#语言规范5.0中文版中比较运算符的描述如下: 2.通用类型系统 3.值类 ...
- The connection string name is missing for the MySqlSiteMapProvider
在ASP.NET-WebForm程序中,添加SiteMapPath控件时出现问题,如下图所示: 解决办法:找到上图源文件指向的machine.config配置文件,将siteMap节点注释即可.
- webservice因引用Oracle.DataAccess.dll导致发布前预编译不通过
这个问题最初是什么问题已经忘了,虽然就在几小时前/