数据库设计 表和表之间的三种关系
表与表之间一般存在三种关系,即一对一,一对多,多对多关系。
下面分别就三种关系讲解数据库相关设计的思路和思考过程;
(1)一对一关系
例如,下面的一张表,保存了人的相关信息,有男有女,要求查处所有的夫妻。
sql代码:
CREATE TABLE IF NOT EXISTS person(id INT PRIMARY KEY AUTO_INCREMENT,sname VARCHAR(10),sex CHAR(1),husband INT,wife INT
);
INSERT INTO person VALUES(1,'小花','0',3,0);
INSERT INTO person VALUES(2,'小明','1',0,4);
INSERT INTO person VALUES(3,'张三','1',0,1);
INSERT INTO person VALUES(4,'小丽','0',2,0);
INSERT INTO person VALUES(5,'王五','1',0,0);
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
sql代码对应的person表:
从表中可以看出,小花和张三是夫妻,小明和小丽是夫妻。通常为了查询方便,需要两个表,但实际项目中为了省空间,通常只建一个表,要实现一对一查询,可以建立两个视图(虚表)
* 有个小细节提一下,视图只是个逻辑概念,并不独立占用物理内存,它依附于数据表,对视图进行修改时相应的表数据也会盖改动*
CREATE VIEW men AS (SELECT * FROM person WHERE sex='1');
CREATE VIEW women AS (SELECT * FROM person WHERE sex='0');
- 1
- 2
men视图:
women视图:
执行查询:
方式一(原始方法):SELECT men.sname AS husband,women.sname AS wife FROM men,women WHERE men.id = women.husband AND women.id = men.wife;
方式二(连接方法):SELECT men.sname AS husband,women.sname AS wife FROM men INNER JOIN women ON men.id = women.husband AND women.id = men.wife;
二、一对多关系
例如:一个人可以拥有多辆汽车,要求查询某个人拥有的所有车辆。
分析:这种情况其实也可以采用 一张表,但因为一个人可以拥有多辆汽车,如果采用一张表,会造成冗余信息过多。好的设计方式是,人和车辆分别单独建表,那么如何将两个表关联呢?有个巧妙的方法,在车辆的表中加个外键字段(人的编号)即可。
* (思路小结:’建两个表,一’方不动,’多’方添加一个外键字段)*
sql代码:
//建立人员表
CREATE TABLE human(id VARCHAR(12) PRIMARY KEY,sname VARCHAR(12),age INT,sex CHAR(1)
);
INSERT INTO human VALUES('H001','小王',27,'1');
INSERT INTO human VALUES('H002','小明',24,'1');
INSERT INTO human VALUES('H003','张慧',28,'0');
INSERT INTO human VALUES('H004','李小燕',35,'0');
INSERT INTO human VALUES('H005','王大拿',29,'1');
INSERT INTO human VALUES('H006','周强',36,'1');//建立车辆信息表
CREATE TABLE car(id VARCHAR(12) PRIMARY KEY,mark VARCHAR(24),price NUMERIC(6,2),hid VARCHAR(12),CONSTRAINT fk_human FOREIGN KEY(hid) REFERENCES human(id)
);
INSERT INTO car VALUES('C001','BMW',65.99,'H001');
INSERT INTO car VALUES('C002','BenZ',75.99,'H002');
INSERT INTO car VALUES('C003','Skoda',23.99,'H001');
INSERT INTO car VALUES('C004','Peugeot',20.99,'H003');
INSERT INTO car VALUES('C005','Porsche',295.99,'H004');
INSERT INTO car VALUES('C006','Honda',24.99,'H005');
INSERT INTO car VALUES('C007','Toyota',27.99,'H006');
INSERT INTO car VALUES('C008','Kia',18.99,'H002');
INSERT INTO car VALUES('C009','Bentley',309.99,'H005');
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
sql代码对应的人员表:
sql代码对应的车辆信息表:
执行查询:SELECT human.sname AS 车主,car.mark AS 车辆 FROM human,car WHERE human.id = car.hid;
`SELECT human.sname AS 车主,car.mark AS 车辆 FROM human INNER JOIN car WHERE human.id = car.hid;
三、多对多关系`
例如:学生选课,一个学生可以选修多门课程,每门课程可供多个学生选择。
分析:这种方式可以按照类似一对多方式建表,但冗余信息太多,好的方式是实体和关系分离并单独建表,实体表为学生表和课程表,关系表为选修表,其中关系表采用联合主键的方式(由学生表主键和课程表主键组成)建表。
sql代码:
//建立学生表
CREATE TABLE student(id VARCHAR(10) PRIMARY KEY,sname VARCHAR(12),age INT,sex CHAR(1),class VARCHAR(6)
);
INSERT INTO student VALUES('p0001','王军',20,1,'c101');
INSERT INTO student VALUES('p0002','张宇',21,1,'c101');
INSERT INTO student VALUES('p0003','刘飞',22,1,'c102');
INSERT INTO student VALUES('p0004','赵燕',18,0,'c103');
INSERT INTO student VALUES('p0005','曾婷',19,0,'c103');
INSERT INTO student VALUES('p0006','周慧',21,0,'c104');
INSERT INTO student VALUES('p0007','小红',23,0,'c104');
INSERT INTO student VALUES('p0008','杨晓',18,0,'c104');
INSERT INTO student VALUES('p0009','李杰',20,1,'c105');
INSERT INTO student VALUES('p0010','张良',22,1,'c105');//建立课程表
CREATE TABLE course(id VARCHAR(10) PRIMARY KEY,sname VARCHAR(12),credit NUMERIC(2,1),teacher VARCHAR(12)
);
INSERT INTO course VALUES('C001','Java',3.5,'李老师');
INSERT INTO course VALUES('C002','高等数学',5.0,'赵老师');
INSERT INTO course VALUES('C003','JavaScript',3.5,'王老师');
INSERT INTO course VALUES('C004','离散数学',3.5,'卜老师');
INSERT INTO course VALUES('C005','数据库',3.5,'廖老师');
INSERT INTO course VALUES('C006','操作系统',3.5,'张老师');//建立选修表
CREATE TABLE sc(sid VARCHAR(10),cid VARCHAR(10)
);ALTER TABLE sc ADD CONSTRAINT pk_sc PRIMARY KEY(sid,cid);
ALTER TABLE sc ADD CONSTRAINT fk_student FOREIGN KEY(sid) REFERENCES student(id);
ALTER TABLE sc ADD CONSTRAINT fk_course FOREIGN KEY(cid) REFERENCES course(id);INSERT INTO sc VALUES('S0001','C001');
INSERT INTO sc VALUES('S0001','C002');
INSERT INTO sc VALUES('S0001','C003');
INSERT INTO sc VALUES('S0002','C001');
INSERT INTO sc VALUES('S0002','C004');
INSERT INTO sc VALUES('S0003','C002');
INSERT INTO sc VALUES('S0003','C005');
INSERT INTO sc VALUES('S0004','C003');
INSERT INTO sc VALUES('S0005','C001');
INSERT INTO sc VALUES('S0006','C004');
INSERT INTO sc VALUES('S0007','C002');
INSERT INTO sc VALUES('S0008','C003');
INSERT INTO sc VALUES('S0009','C001');
INSERT INTO sc VALUES('S0009','C005');
- 1
- 2
- 3
- 4
- 5
- 6
- 7
- 8
- 9
- 10
- 11
- 12
- 13
- 14
- 15
- 16
- 17
- 18
- 19
- 20
- 21
- 22
- 23
- 24
- 25
- 26
- 27
- 28
- 29
- 30
- 31
- 32
- 33
- 34
- 35
- 36
- 37
- 38
- 39
- 40
- 41
- 42
- 43
- 44
- 45
- 46
- 47
- 48
- 49
- 50
- 51
- 52
- 53
- 54
- 55
- 56
- 57
sql代码对应的学生表:
sql代码对应的课程表:
sql代码对应的选课表:
执行查询:(没有选课的学生信息和无学生选的课程信息)
普通方式:
SELECT * FROM student WHERE student.id NOT IN (SELECT sid FROM sc);
SELECT * FROM course WHERE course.id NOT IN (SELECT cid FROM sc);
- 1
- 2
关联方式:
SELECT student.* FROM student LEFT JOIN sc ON student.id=sc.sid LEFT JOIN course ON course.id = sc.cid WHERE course.sname IS NULL;
SELECT course.* FROM course LEFT JOIN sc ON course.id=sc.cid LEFT JOIN student ON student.id = sc.sid WHERE studen
数据库设计 表和表之间的三种关系相关推荐
- SQL外键foreign key 表与表之间的三种关系
表与表之间的三种关系 多对一关系表 注意事项: 一对多表关系,外键字段建在多的一方. 在创建表的时候,一定要先建被关联表. 在录入数据的时候,也必须先录入被关联表. 删除 一定要先删除主键表,才可以删 ...
- MySql数据库三种关系详解
如何分辨三种关系,以及三种关系的图列对比. 1.分析三种关系. 是否左表的多条记录可以对应右表的一条记录,是,则证明左表的一个字段 关联(foreign key)右表的一个字段(通常为ID) 是否右表 ...
- 数据库设计(表与表之间的3种关系)
表与表之间一般存在三种关系,即一对一,一对多,多对多关系. 下面分别就三种关系讲解数据库相关设计的思路和思考过程: (1)一对一关系 例如,下面的一张表,保存了人的相关信息,有男有女,要求查处所有 ...
- 数据库设计中常见表结构的设计技巧(转)
2019独角兽企业重金招聘Python工程师标准>>> 一.树型关系的数据表 不少程序员在进行数据库设计的时候都遇到过树型关系的数据,例如常见的类别表,即一个大类,下面有若干个子类, ...
- python 全栈开发,Day62(外键的变种(三种关系),数据的增删改,单表查询,多表查询)...
一.外键的变种(三种关系) 本节重点: 如何找出两张表之间的关系 表的三种关系 一.介绍 因为有foreign key的约束,使得两张表形成了三种了关系: 多对一 多对多 一对一 二.重点理解如果找出 ...
- 统计内表行数常用的三种方法
以下是统计内表行数常用的三种方法, 如下: 1.LOOP AT it_itab. g_lines2 = g_lines2 + 1. ENDLOOP. 该方法是通过循环内部表自己累 ...
- php表单数据类型,form表单中enctype属性的三种类型
1.form表单中enctype属性的三种类型 form表单中enctype属性可以用来控制对表单数据的发送前的如何进行编码,enctype有三种,分别为: multipart/form-data不对 ...
- 数据库设计(ER模型和UML模型及转换为关系模型的公式)
本文根据b站鲁老师的教学视频整理而来,可能会偏理论化,有点枯燥,但是如果认真看完,还是会有所收获哒. 从本文可以学习到: 对于一个即将展开的项目,我们应该怎么设计及实现数据库. 掌握概念模型(ER模型 ...
- Hibernate关联映射-数据对象三种关系
Hibernate框架基于ORM设计思想,它将关系型数据库中的表与我们java中的类进行映射,一个对象就对应着表中的一条记录,而表中的字段对应着类中的属性. 数据库中表与表之间存在着三种关系,也就是系 ...
- (转)Hibernate关联映射——对象的三种关系
http://blog.csdn.net/yerenyuan_pku/article/details/70148618 Hibernate关联映射--对象的三种关系 Hibernate框架基于ORM设 ...
最新文章
- MVC3 基本业务开发框架(强转)
- 如何让类对象只在栈(堆)上分配空间?(转)
- Mybatisplus用updateById默认没有传的值不会进行改变
- css x轴不滚动_泡沫轴滚动放松是什么原理:你并不了解泡沫轴
- Solaris 10 ftp,telnet,ssh,sendmail
- java 使用适当的签名_java11教程--类SignatureSpi用法
- asp td tr 高度_ASP.NET Core Blazor 初探之 Blazor Server
- Linux关机重启指令
- Android Studio无法检测到魅族手机的解决方法
- 人脸活体检测人脸识别:眨眼+张口
- CentOS7 安装 YApi
- 国际服登陆显示服务器维护中,国际服显示服务器在维护中怎么办 教你一招解决服务器维护中什么意思...
- ap mt7260a 华硕_MT7620A路由刷DDWRT 及2.4G无线设置经验
- python三阶魔方_三阶魔方自动求解及动态可视化matlab代码
- 适用于Android手机的汉信码识别SDK
- html中怎样隐藏列,关于jquery:隐藏/显示HTML表中的列
- Eventide 2022假日活动
- harbor搭建-主从复制
- Android-app内部调整字体大小
- 小米球ngrok 给你惊喜