数据库设计三大范式

在设计关系型数据库时,遵从不同的规范要求,设计出合理的关系型数据库,这些不同的规范要求就被称为不同的范式,也就是说,范式是符合某一种设计要求的总结。要想设计一个结构合理的关系型数据库,必须满足一定的范式。此外,各种范式呈递次规范,越高的范式数据库冗余越小。满足最低要求的范式是第一范式(1NF)。在第一范式的基础上进一步满足更多规范要求的称为第二范式(2NF),其余范式以次类推。一般说来,数据库只需满足第三范式(3NF)就行了。

本文主要介绍在实际开发中这三种最为常见的范式:

1.第一范式(1NF):(属性的原子性约束--属性不可分解)

第一范式是最基本的范式。如果数据库表中的所有字段值都是不可分解的原子值,就说明该数据库表满足了第一范式。所以,属性下的数据不能是集合,数组,记录等非原子数据项。实体中的某个属性有多个值时,必须拆分为不同的属性。

比如,一个学生选课系统,先设计学生表,内容包括:学号、学生姓名、年龄、性别、课程名称、课程学分、学科成绩、系别、系办地址、系办电话信息。

学生表
学号 学生姓名 年龄 性别 课程名称 课程学分 学科成绩 系别 系办地址 系办电话
001 张三 24 《数据结构》 4 82.0 计算机系 10号楼 123456
002 李四 25 《数据结构》 4 79.5 计算机系 10号楼 123456
003 王五 25 《数据结构》 4 85.0 计算机系 10号楼 123456
004 赵六 25 《数据结构》 4 78.0 数学系 6号楼 456789
001 张三 24 《C语言》 3 85.0 计算机系 10号楼 123456
002 李四 25 《C语言》 3 78.0 计算机系 10号楼 123456
003 王五 25 《C语言》 3 79.5 计算机系 10号楼 123456
004 赵六 25 《C语言》 3 81.0 数学系 10号楼 456789
                   

以上数据表满足第一范式。可以看到,数据库表中的字段都是单一属性的,不可再分。这个单一属性由基本类型构成,包括整型、实数、字符型、逻辑型、日期型等。在当前的任何关系数据库管理系统(DBMS)中, 不可能做出不符合第一范式的数据库,因为这些DBMS不允许你把数据库表的一列再分成二列或多列,比如“电话”这个属性下不能同时存手机号码和座机号码(不好区分),要分开字段存储。因此,你想在现有的DBMS中设计出不符合第一范式的数据库都是不可能的。

其实任何复杂的系统,只要数据信息可以发生关联,我们都可以合并设计成一个表结构。但是,这样的数据库表结构设计合理吗?

问题分析

a、依赖关系:该学生表中,课程学分依赖于课程名称,而不依赖于学号。

b、数据冗余:同一门课程的学分相同,采用该学生表存储数据的话,对相同的课程存储相同的课程学分,会造成数据冗余,浪费存储空间。

c、数据更新异常:若更改某一门课程的学分,则该表中其他所有相同课程的学分都要更改,操作复杂;若需要新增一门课程,因为缺乏其他字段(如学号、学生姓名等)信息,导致数据插入困难。

d、数据删除异常:如果部分学生毕业了,学生记录会随之删除,该表中,删除学生信息同时也会删除课程名称、课程学分等信息,这自然不可取。

为了解决以上问题,我们引入接下来需要介绍的范式。

2.第二范式(2NF):(记录的惟一性约束--添加主键,非主键字段都和主键相关)

第二范式在第一范式基础上,要求数据库表中的每个实例或记录必须可以被唯一地区分。比如在学生表中,学号可以唯一确定一个学生,而其他属性对不同的学生而言,有相同的可能。这时,学号就可以作为学生表的主键。此外,第二范式要求:实体的属性完全依赖于主关键字。所谓完全依赖是指不能存在仅依赖主关键字一部分的属性,如果存在,那么这个属性和主关键字的这一部分应该分离出来形成一个新的实体,新实体与原实体之间是一对多的关系。为实现区分通常需要为表加上一个列,以存储各个实例的唯一标识。简而言之,第二范式就是在第一范式的基础上属性完全依赖于主键

为了解决第一范式表中的问题,我们把学生表和课程表以及选课关系分离,如下所示

学生表
学号 学生姓名 年龄 性别 系别 系办地址 系办电话
001 张三 24 计算机系 10号楼 123456
002 李四 25 计算机系 10号楼 123456
003 王五 25 计算机系 10号楼 123456
004 赵六 25 数学系 6号楼 456789
001 张三 24 计算机系 10号楼 123456
002 李四 25 计算机系 10号楼 123456
003 王五 25 计算机系 10号楼 123456
004 赵六 25 数学系 10号楼 456789
             

课程表
课程名 课程学分
《数据结构》 4
《C语言》 3
   
   

选课关系表
学号 课程名称 成绩
001 《数据结构》 82.0
002 《数据结构》 79.5
003 《数据结构》 85.0
004 《数据结构》 78.0
001 《C语言》 85.0
002 《C语言》 78.0
003 《C语言》 79.5
004 《C语言》 81.0
     

3.第三范式(3NF):(字段冗余性约束--确保每列都和主键列直接相关,而不是间接相关)

第三范式需要确保数据表中的每一列数据都和主键直接相关,而不能间接相关

我们看第二范式中的学生表,学号作为主关键字,因为存在如下决定关系:

(学号)→ (姓名,年龄,性别,系别,系办地址、系办电话)
但是还存在下面的决定关系
(学号) → (系别)→(系办地点,系办电话)
即存在非关键字段"系办地点"、"系办电话"对关键字段"学号"的传递函数依赖。它也会存在数据冗余、更新异常、插入异常和删除异常的情况。
根据第三范式把学生表细分为如下两个表就可以满足第三范式了:
学生表
学号 学生姓名 年龄 性别 系别
001 张三 24 计算机系
002 李四 25 计算机系
003 王五 25 计算机系
004 赵六 25 数学系
001 张三 24 计算机系
002 李四 25 计算机系
003 王五 25 计算机系
004 赵六 25 数学系
         

系别表
系别 系办地址 系办电话
计算机系 10号楼 123456
数学系 6号楼 456789
     


以上细分的最后的数据库表集合就是符合I,Ⅱ,Ⅲ范式的,消除了数据冗余、更新异常、插入异常和删除异常。

转载请注明出处:
http://blog.csdn.net/daijin888888/article/details/51219218

你可能感兴趣的:(数据库)