数据库建表范式
本文于1220天之前发表,文中内容可能已经过时。
设计口诀:
多对多:
多对多三张表,关系表辆外键一对多:
一对多两张表,多的表加外键一对一(一张表拆分, 一对多特殊形式,如用户详细信息和简要信息):
- 主键共享
- 外键唯一
范式的目的
按照三范式设计的表不会出现冗余
第一范式
任何一张表都应该有主键, 并且每个字段原子不可再分
学生学号 | 学生姓名 | 联系方式 |
---|---|---|
1001 | 张三 | zhangsan@xx.com, 13xxxxxxx |
1002 | 李四 | lisi@xx.com, 13xxxxxxx |
联系方式可再分
更改后
学生学号 | 学生姓名 | 电话 | |
---|---|---|---|
1001 | 张三 | zhangsan@xx.com | 13xxxxxxx |
1002 | 李四 | lisi@xx.com | 13xxxxxxx |
第二范式
建立在第一范式之上,所有的非主键字段完全依赖主键,不能产生部分依赖
学生学号 | 学生姓名 | 教师编号 | 教师姓名 |
---|---|---|---|
1001 | 张三 | 001 | 赵老师 |
1002 | 李四 | 002 | 陈老师 |
1001 | 张三 | 002 | 陈老师 |
满足第一范式吗? 不满足,因为没有主键
关系为 多对多
所以确定主键
学生学号(PK) | 教师编号(PK) | 学生姓名 | 教师姓名 |
---|---|---|---|
1001 | 001 | 张三 | 赵老师 |
1002 | 002 | 李四 | 陈老师 |
1001 | 002 | 张三 | 陈老师 |
此时,复合主键已经满足第一范式,但是不满足第二范式,此时存在数据冗余
多对多:三张表,关系表辆外键
学生表
sNo(PK) | 姓名 |
---|---|
1 | 张胜 |
2 | 李四 |
3 | 王五 |
老师表
tNo(PK) | 姓名 |
---|---|
1 | 王老师 |
2 | 张老师 |
3 | 李老师 |
关系表
id(PK) | sno(fk) | tno(fk) |
---|---|---|
1 | 1 | 3 |
2 | 1 | 1 |
3 | 2 | 2 |
4 | 2 | 3 |
5 | 3 | 1 |
6 | 3 | 3 |
第三范式
建立在第二范式基础上,所有非主键字段直接依赖主键,不能产生传递依赖
如学生班级表 一对多关系
学生学号(PK) | 学生姓名 | 班级编号 | 班级名称 |
---|---|---|---|
1001 | 张三 | 1 | 一年一班 |
1002 | 李四 | 2 | 一年二班 |
1001 | 张三 | 3 | 一年三班 |
1001 | 张三 | 4 | 一年四班 |
班级名称依赖于班级编号,但是班级编号依然依赖于学生学号(因为是主键)
一对多? 两张表多的表加外键
班级表t_class
cno(pk) | cname |
---|---|
1 | 一班 |
2 | 二班 |
学生表t_student
sno(pk) | sname | classno(fk) |
---|---|---|
1 | 张三 | 1 |
2 | 李四 | 1 |
3 | 王五 | 2 |
4 | 周六 | 2 |
5 | 马五 | 2 |
一对多表设计
t_user_login 用户登录表
sno(pk) | sname | classno(fk) |
---|---|---|
1 | 张三 | 1 |
2 | 李四 | 1 |
t_user_detail 用户详细信息表(主键共享 主键为t_user_login的主键)
id(pk+fk) | realname | tel | … |
---|---|---|---|
1 | 张三 | 138xxxxx | … |
2 | 李四 | 138yyyyy | … |
t_user_detail 用户详细信息表(外键唯一约束)
id(pk) | realname | tel | userid(fk+unique) |
---|---|---|---|
1 | 张三 | 138xxxxx | 2 |
2 | 李四 | 138yyyyy | 1 |
赏
支付宝打赏
微信打赏
您的支持是我前行的动力!