以如下关系为例:
Student(
Sno 学号 主键
Sdept 专业
Mname 系主任姓名
Cno 课程号 主键
Grade 成绩
)
可能出现的问题:
数据冗余+增删改异常
数据冗余
如果一个系有100名学生,每人选择3门课,那么Sdept和Mname这两条数据就会重复300次,极大占用了储存空间。
增
如果一个学生尚未选课,由于课程号是主键,会导致在录入学生信息时无法添加(主键不能为NULL)。
删
如果课程结束,所有数据被清空,会导致查询学生的专业以及系主任姓名也无法查询。
改
若系主任更换,则整个表的所有元组都要修改。
那么出现这些问题的原因是什么?
不合适的数据依赖关系
分析以下数据依赖关系:
(Sno, Cno) → Grade
(Sno,Cno) → Sdept → Cno
很显然,学号和课程号共同决定一名学生某一门课程的成绩;而决定一个学生的专业和系主任则只需要学号就足够,而与学生所选课程号没有任何关系。
数据依赖关系分为:
函数依赖:y = f(x)
多值依赖:x = f(y)
多值依赖是不应该出现在数据库中的,它会导致主键无法决定唯一的元组。
而在函数依赖中,也分为以下情况:
完全依赖 | 部分依赖
传递依赖
平凡依赖 | 非平凡依赖
其中加粗的项都是不应该出现的依赖类型
部分依赖: 函数依赖关系由主键的真子集就能唯一确定。
传递依赖: 数据函数依赖于一项函数依赖于另一项数据的数据。
平凡依赖: 主键的子集函数依赖于主键,这是显然的,但也是没有意义的。
为了避免这些错误出现,就要遵循特定的规范化规则。