数据库范式详细介绍(1NF,2NF,3NF,BCNF,4NF)
怎么拍一拍对方⼀、基本介绍
设计关系数据库时,遵从不同的规范要求,设计出合理的关系型数据库,这些不同的规范要求被称为不同的范式,各种范式呈递次规范,越⾼的范式数据库冗余越⼩。
⽬前关系数据库有六种范式:第⼀范式(1NF)、第⼆范式(2NF)、第三范式(3NF)、巴斯-科德范式(BCNF)、第四范式(4NF)和第五范式
(5NF,⼜称完美范式)。满⾜最低要求的范式是第⼀范式(1NF)。在第⼀范式的基础上进⼀步满⾜更多规范要求的称为第⼆范式(2NF),其余范式以次类推。⼀般说来,数据库只需满⾜第三范式(3NF)就⾏了。
范式的包含关系。⼀个数据库设计如果符合第⼆范式,⼀定也符合第⼀范式。如果符合第三范式,⼀定也符合第⼆范式…
数据库基本概念
要理解范式,⾸先必须对知道什么是关系数据库,简单的说:关系数据库就是⽤⼆维表来保存数据。表和表之间可以……(省略10W 字),如果对数据库很熟悉,可以不⽤理会下⾯的概念。
实体:现实世界中客观存在并可以被区别的事物。⽐如“⼀个学⽣”、“⼀本书”、“⼀门课”等等。值得强调的是这⾥所说的“事物”不仅仅是看得见摸得着的“东西”,它也可以是虚拟的,不如说“⽼师与学校的关系”。
属性:教科书上解释为:“实体所具有的某⼀特性”,由此可见,属性⼀开始是个逻辑概念,⽐如说,“性别”是“⼈”的⼀个属性。在关系数据库中,属性⼜是个物理概念,属性可以看作是“表的⼀列”。
元组:表中的⼀⾏就是⼀个元组。
分量:元组的某个属性值。在⼀个关系数据库中,它是⼀个操作原⼦,即关系数据库在做任何操作的时候,属性是“不可分的”。否则就不是关系数据库了。
码:表中可以唯⼀确定⼀个元组的某个属性(或者属性组),如果这样的码有不⽌⼀个,那么⼤家都叫候选码,我们从候选码中挑⼀个出来做⽼⼤,它就叫主码。
全码:如果⼀个码包含了所有的属性,这个码就是全码。
主属性:⼀个属性只要在任何⼀个候选码中出现过,这个属性就是主属性。
⾮主属性:与上⾯相反,没有在任何候选码中出现过,这个属性就是⾮主属性。
外码:⼀个属性(或属性组),它不是码,但是它别的表的码,它就是外码。
候选码: 若关系中的某⼀属性或属性组的值能唯⼀的标识⼀个元组,⽽其任何真⼦集都不能再标识,则称该属性组为(超级码)候选码。
⼆、6种范式
前⾯说到,范式越⾼,数据的冗余度越⼩。其实没有冗余的数据库设计是可以做到的。但是,没有冗余的数据库未必是最好的数据库,有时为了提⾼运⾏效率,就必须降低范式标准,适当保留冗余数据。具体做法是:在概念数据模型设计时遵守第三范式,降低范式标准的⼯作放到物理数据模型设计时考虑。降低范式就是增加字段,允许冗余。(最典型的就是在⼀些数据表中不仅存作为外键的user_id,同样存
user_name,这样虽然违反数据库范式增加了user_name字段,但是却提⾼了效率,减少了获取user_id后再去user表中获取user name的操作)
中国的风俗习惯所以实际中,我们只需要考虑数据库满⾜第三范式就可以了,下⾯以最通俗的⽅式来解释数据库的范式。
第⼀范式(1NF):属性不可分
1NF的定义为:符合1NF的关系中的每个属性都不可再分
例⼦⼀:
如上图所⽰的情况,就不符合1NF的要求。
实际上,1NF是所有关系型数据库的最基本要求,你在关系型数据库管理系统(RDBMS),例如SQL Server,Oracle,MySQL中创建数据表的时候,如果数据表的设计不符合这个最基本的要求,那么操作⼀定是不能成功的。也就是说,只要在RDBMS中已经存在的数据表,⼀定是符合1NF的。如果我们要在RDBMS中表现表中的数据,就得设计为如下图的形式:
例⼦⼆:
如上图所⽰的情况,就不符合1NF的要求。
如果我们要在RDBMS中表现表中的数据,就得设计为如下图的形式:
第⼆范式(2NF):符合1NF,并且⾮主属性完全依赖于码。
长字开头的成语满⾜1NF,⾮主属性完全函数依赖于候选码
⼀个候选码中的主属性也可能是好⼏个。如果⼀个主属性,它不能单独做为⼀个候选码,那么它也不能确定任何⼀个⾮主属性。
给⼀个反例:我们考虑⼀个⼩学的教务管理系统,学⽣上课指定⼀个⽼师,⼀本教材,⼀个教室,⼀个时间,⼤家都上课去吧,没有问题。那么数据库怎么设计?(学⽣上课表)
学⽣ 课程 ⽼师 ⽼师职称 教材 教室 上课时间
⼩明 ⼀年级语⽂(上) ⼤宝 副教授 《⼩学语⽂1》 101 14:30
⼀个学⽣上⼀门课,⼀定在特定某个教室。所以有(学⽣,课程)->教室
⼀个学⽣上⼀门课,⼀定是特定某个⽼师教。所以有(学⽣,课程)->⽼师
⼀个学⽣上⼀门课,他⽼师的职称可以确定。所以有(学⽣,课程)->⽼师职称
⼀个学⽣上⼀门课,⼀定是特定某个教材。所以有(学⽣,课程)->教材
⼀个学⽣上⼀门课,⼀定在特定时间。所以有(学⽣,课程)->上课时间
因此(学⽣,课程)是⼀个码。
然⽽,⼀个课程,⼀定指定了某个教材,⼀年级语⽂肯定⽤的是《⼩学语⽂1》,那么就有课程->教材。(学⽣,课程)是个码,
(学⽣,课程)->教材有课程->教材存在⾮主属性对码(学⽣,课程)s的部分函数依赖。
课程却决定了教材,这就叫做不完全依赖,或者说部分依赖。出现这样的情况,就不满⾜第⼆范式 !有什么不好吗?你可以想想:教师自我介绍范文
校长要新增加⼀门课程叫“微积分”,教材是《⼤学数学》,怎么办?学⽣还没选课,⽽学⽣⼜是主属性,主属性不能空,课程怎么记录呢,教材记到哪呢? ……郁闷了吧?(插⼊异常)
下学期没学⽣学⼀年级语⽂(上)了,学⼀年级语⽂(下)去了,那么表中将不存在⼀年级语⽂(上)
,也就没了《⼩学语⽂1》。这时候,校长问:⼀年级语⽂(上)⽤的什么教材啊?……郁闷了吧?(删除异常)
校长说:⼀年级语⽂(上)换教材,换成《⼤学语⽂》。有10000个学⽣选了这么课,改动好⼤啊!改累死了……郁闷了吧?(修改异常)
那应该怎么解决呢?们必须消除这些部分函数依赖,只有⼀个办法,就是将⼤数据表拆分成两个或者更多个更⼩的数据表,在拆分的过程中,要达到更⾼⼀级范式的要求,这个过程叫做”模式分解“。模式分解的⽅法不是唯⼀的,以下是其中⼀种⽅法:将⼀个表分解成两个或若⼲个表。
教师节送什么花好
学⽣表
学⽣ 课程 ⽼师 ⽼师职称 教室 上课时间
⼩明 ⼀年级语⽂(上) ⼤宝 副教授 101 14:30
课程表
课程 教材
⼀年级语⽂(上) 《⼩学语⽂1》
(这⾥还涉及到⼀个如何进⾏模式分解才是正确的知识点,先不介绍了)
现在我们来看⼀下,进⾏同样的操作,是否还存在着之前的那些问题?
1. ⼀年级语⽂(上)换教材,换成《⼤学语⽂》
只需要修改⼀次⼀年级语⽂(上)对应的教材的值即可。——有改进
2. 下学期没学⽣学⼀年级语⽂(上)了,学⼀年级语⽂(下)去了,那么表中将不存在⼀年级语⽂(上),也就没了《⼩学语⽂1》。
该教材尚在。——有改进
3. 删除⽼师中所有的学⽣记录
该⽼师的信息仍然全部丢失。——⽆改进
4. 插⼊⼀个尚⽆学⽣的新⽼师的信息。
因为学⽣表的码是学⽣和课程,不能为空,所以此操作不被允许。——⽆改进
所以说,仅仅符合2NF的要求,很多情况下还是不够的,⽽出现问题的原因,在于仍然存在⾮主属性系主任对于码学号的传递函数依赖。为了能进⼀步解决这些问题,我们还需要将符合2NF要求的数据表改进为符合3NF的要求。
第三范式(3NF):符合2NF,并且消除了⾮主属性对于候选码的传递函数依赖。
如果存在⾮主属性对于码的传递函数依赖,则不符合3NF的要求。
接下来我们看看上⾯2NF图中的设计,是否符合3NF的要求。
对于课程表,主码为课程,主属性为课程,⾮主属性只有⼀个,为教材,不可能存在传递函数依赖,
所以表2的设计,符合3NF的要求。
对于学⽣表,主码为(学⽣,课程),主属性为学⽣和课程,⾮主属性为⽼师、⽼师职称和教室。因为(学⽣,课程) → ⽼师,同时⽼师 → ⽼师职称,所以存在⾮主属性系⽼师对于码(学⽣,课程)的传递函数依赖,所以表1的设计,不符合3NF的要求。
为了让数据表设计达到3NF,我们必须进⼀步进⾏模式分解为以下形式:
学⽣表(学⽣,课程,⽼师,教室,上课时间)
课程表(课程,教材)
⽼师表(⽼师,⽼师职称)
上海浦东移动营业厅对于课程表,符合3NF的要求,之前已经分析过了。
对于学⽣表,码为(学⽣,课程),主属性为学⽣和课程,⾮主属性为⽼师、教室和上课时间,不可能存在⾮主属性对于码的传递函数依赖,所以符合3NF的要求。
对于⽼师表,码为⽼师,主属性⽼师,⾮主属性为⽼师职称,不可能存在⾮主属性对于码的传递函数依赖(⾄少要有三个属性才可能存在传递函数依赖关系),所以符合3NF的要求。
学⽣表
学⽣ 课程 ⽼师 教室 上课时间
⼩明 ⼀年级语⽂(上) ⼤宝 101 14:30
课程表
课程 教材
⼀年级语⽂(上) 《⼩学语⽂1》
⽼师表
⽼师 ⽼师职称
⼤宝 副教授
现在我们来看⼀下,进⾏同样的操作,是否还存在着之前的那些问题?
1. 删除某个⽼师中所有的学⽣记录
该⽼师的信息不会丢失。——有改进
2. 插⼊⼀个尚⽆学⽣的新⽼师的信息。
因为⽼师表与学⽣表⽬前是独⽴的两张表,所以不影响。——有改进
BCNF:符合3NF,并且消除主属性对于码的部分与传递函数依赖
满⾜3NF,消除每⼀属性对候选码的部分与传递依赖
举例⼀:若⼀张表的数据包括:“书号、书名、作者”其中,书号是唯⼀的,书名允许相同,⼀个书号对应⼀本书。⼀本书的作者可以多个,但是同⼀个作者所参与编著的书名应该是不同,希望没有说晕,看图看图。
存在关系:
书号→书名
(书名、作者)→书号
其中,每⼀个属性都为主属性,但是上述关系存在传递依赖,不能是BCNF。即:
(书名、作者)→书号→书名
(书名、作者)→书名
即出现主属性书号对(书名,作者)码的传递依赖
我们可以通过分解为两张表,实现BCNF。
举例⼆:某公司有若⼲个仓库,每个仓库只能有⼀名管理员,⼀名管理员只能在⼀个仓库中⼯作;⼀个仓库中可以存放多种物品,⼀种物品也可以存放在不同的仓库中。每种物品在每个仓库中都有对应的数量。那么关系模式仓库(仓库名,管理员,物品名,数量)属于哪⼀级范式?
答:已知函数依赖集:
仓库名 → 管理员,管理员 → 仓库名,(仓库名,物品名)→ 数量
码:(管理员,物品名),(仓库名,物品名)
主属性:仓库名、管理员、物品名⾮主属性:数量
版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系QQ:729038198,我们将在24小时内删除。
发表评论