数据库范式
应用数据库范式可以带来许多好处:
① 减少数据冗余。
② 消除异常(插入异常,更新异常,删除异常)
③ 让数据组织的更加和谐。
但是数据库的范式绝对不是越高越好,范式越高,意味着表越多,多表联合查询的纪律就越大,SQL查询的效率就变低。
第一范式(1NF)
第一范式要求数据库中的每一列都保持原子特性。
列都是基本数据项,不能够再进行分割,否则设计成一对多的实体关系。
例如:有一个学生表,其中包含的字段有:学号
、姓名
、班级
、年龄
、地址
。
这个学生表,就没有遵循第一范式。这是因为表中的地址字段,还可以细分为:省,市,区等不可再分割的字段。
如果将上面的学生表进行改造的话,按照第一范式的要求,则拆分改造后的结构为:
学生表(学号,姓名,年龄,地址ID)
地址表(地址ID,省,市,区,街道)
注意:不符合第一范式的数据库表不能称作是关系型数据库。
第二范式(2NF)
首先需要明确一点的是:第二范式是在第一范式的基础上建立起来的,即满足第二范式必须满足第一范式。
第二范式要求非主属性完全依赖于主属性,如果不是完全依赖主键,应该拆分成新的实体,设计成一对多的关系。
大白话就是:第二范式需要确保数据库表中的每一列都和主键相关,而不是只与主键的一部分相关(指针联合主键)
举个例子:
选课关系表(学号,姓名,年龄,课程名称,成绩,学分),主属性为联合主键(学号,课程名称)。
因此存在下面的依赖关系:
姓名
、年龄
这两个字段依赖于学号
字段。 即通过学号,我们才能知道学生的姓名和年龄。 (学号) -> (姓名、年龄)
成绩
,学分
依赖于 课程名称
。即只有知道了课程名称,我们才能知道该课程的成绩和学分。(课程名称) -> (成绩、学分)
这个数据库表就不满足第二范式,因为,它的非主属性是部分依赖主键的。学分
和 学号
这两个属性根本就没有任何依赖关系。
第三范式(3NF)
明确一点:第三范式是在第二范式的基础上建立起来的。
第三范式要求:属性不依赖于其他非主属性。即每个非主属性都应该与主属性有直接关系,而不是间接关系。
举个例子:现在存在:
学生表(学号、姓名、年龄、学院名称、学院电话)
其中主键是学号
。
此时,这个表就不符合第三范式,因为学院电话 是 依赖于 学院名称的,而不是依赖学号的。它们之间存在传递的关系:
学号 -> 学院名称 -> 学院电话。
我们对学生表进行改造:
学生表(学号、姓名、年龄、学院ID)
学院表(学院ID、学院名称、学院电话)
此时,通过学号我们可以知道学生的姓名、年龄、和所在学院的ID号。
通过学院ID,我们可以知道学院名称和学院电话。
此时,我们上面新改造的两个表中,非主属性都是依赖于主属性的,且非主属性都不依赖于其他非主属性,满足MySQL的三大范式。