一、数据库三级模式两级映射
二、数据库设计过程说明
三、E-R图
1:1一对一
两个实体之间是一对一的关系,一个班主任管理一个班级,一个班级只有一个班主任。
在1:1的关系中,在任意端的关系中选择一个要添加另一端实体的主键。
1:1的E-R图转换关系模式,2个实体中间的联系可以归并到任意一边,也可以自成一个实体;
1:1的E-R图转换关系模式关系模式 (联系无属性)
归到班主任一边
在班主任实体中添加班级实体的主键
班主任(姓名,性别,年龄,班号)
班级(班号,人数)
归到班级一边
在班级实体中添加班主任实体的主键
班主任(姓名,性别,年龄)
班级(班号,人数,姓名)
自成一个实体
联系若无属性则在其中添加两个相连实体的主键
班主任(姓名,性别,年龄)
班级(班号,人数)
管理(姓名,班号)
1:1的E-R图转换关系模式(联系有属性)
归到班主任一边
在班主任实体中添加班级实体的主键+联系本身的属性
班主任(姓名,性别,年龄,班号,每周等级)
班级(班号,人数)
归到班级一边
在班级实体中添加班主任实体的主键+联系本身的属性
班主任(姓名,性别,年龄)
班级(班号,人数,姓名,每周等级)
自成一个实体
在其中添加两个相连实体的主键+联系本身的属性
班主任(姓名,性别,年龄)
班级(班号,人数)
管理(姓名,班号,每周等级)
1:n一对多
两个实体之间是1对多的关系,1个班级里面有多个学生。
在1:n的关系中,在n端的关系中一定要添加1端实体的主键
1:n的E-R图转换关系模式,2个实体中间的联系只能归到多的那一端实体中,也可以自成一个实体;
注:如果无法分清哪端是1哪端是n可以将自己想象为实体;
例如我是班级实体,我可以对应n个学生,那么对端学生就是n;
例如我是学生实体,我只可以对应一个班级,那么对端班级就是1
1:n的E-R图转换关系模式(联系无属性)
归到n端学生一边
在学生实体中添加1端即班级实体的主键
班级(班号,人数)
学生(姓名,学号,性别,班号)
自成一个实体
联系若无属性则在其中添加n端实体的主键
班级(班号,人数)
学生(姓名,学号,性别)
拥有(姓名)
1:n的E-R图转换关系模式(联系有属性)
归到n端产品一边
在n端产品实体中添加1端仓库实体的主键+联系本身的属性
仓库(仓库号,地点,面积)
产品(产品号,产品名,价格,仓库号,数量)
自成一个实体
在其中添加n端实体的主键+联系本身的属性
仓库(仓库号,地点,面积)
产品(产品号,产品名,价格)
仓储(产品号,数量)
m:n多对多
m:n的E-R图转换关系模式,2个实体中间的联系只能自成一个实体,联系实体内容是两端实体主键+联系本身属性;
n:m的E-R图转换关系模式(联系无属性)
自成一个实体
在其中添加2端实体的主键
课程(课程名,任课教师)
学生(姓名,性别,学号)
选修(课程名,姓名)
m:n的E-R图转换关系模式(联系有属性)
自成一个实体
在其中添加2端实体的主键+联系本身属性
课程(课程名,任课教师)
学生(姓名,性别,学号)
选修(课程名,姓名,成绩)
E-R图实例
如遇见较为复杂的关系需要画E-R图时,可以先将各个主体画出然后连接;
例:
集团有多个商店。在其信息系统中,对商店记录有商店编号、商店名、地址等信息;对销售的 商品记录有商品号、商品名、规格、单价等信息;对其 职工记录其职工编号、姓名、性别和业绩等级(优秀、良好、较差)等。每个商店可销 售多种商品,每种商品也可放在多个商店销售,每个商店销售每一种商品,需要记录每月的 销售量;每个商店有许多职工,每个职工只能在一个商店工作,商店聘用职工按照聘期规定 月薪发放工资,每个聘期长度为 1 年。
1、先分别画出实体及其属性
商店
商品
职工
2、实体之间需要有所联系
商店和商品的联系是商店销售商品,进而产生月销售量属性,且一种商品可在多个商店销售,一个商店可以销售多种商品,因而是多对多。
商店和职工的联系是商店聘用职工,进而产生了聘期属性和月薪属性,一个商店可聘用多名职工,一个职工只能被一个商店聘用,因此是一对多
3、最后进行组合
关系模式
写法1:
商店(商店编号,商店名,地址)
商品(商品号,商品名,规格,单价)
销售联系两端是多对多,所以只能自成实体,两端实体主键+联系本身属性
销售(商店编号,商品号,月销售量)
聘用联系两端是1对多,所以归于多端,在多端添加对应1端的主键和联系本身的属性
职工(职工编号,性别,姓名,业绩等级,商店编号,聘期,月薪)
写法2:
商店(商店编号,商店名,地址)
商品(商品号,商品名,规格,单价)
销售联系两端是多对多,所以只能自成实体
销售(商店编号,商品号,月销售量)
职工(职工编号,性别,姓名,业绩等级)
聘用联系两端是1对多,可以自成实体,添加多端的主键+联系本身属性
聘用(职工编号,聘期,月薪)
多实体联系
关系模式
供应商(供应商号,供应商名,地址)
零件(零件号,零件名,单价)
产品(产品号,产品名,型号)
多对多连接,联系自成实体,前3个属性是所联系的3个实体的主键,后一个是联系自身属性
供应(供应商号,零件号,产品号,数量)
例题:
答案:C
图中E-R模型是多对多,关系模型数量是3个实体+联系所成实体 ,共4个关系模式
题型
数据库设计考察形式一般是大题,主考方向是E-R图以及对应关系模式的转换或补充,多个关系模式之间的联系归属问题考究细节。与数据流图类似,需要仔细研读题干信息并将题干信息对应到图中。
一个部门有一个经理,一个经理管理一个部门,经理属于部门员工中一个特殊的员工,用下图表示。
此时经理的关系模式是,经理(员工号,任职时间),要表明是谁当了经理。
四、关系代数
1、并∪
两个表中的数据合在一起,重复的数据只保留一条
2、交 ∩
保留两表中相同的数据
3、笛卡尔积x
表S1中的各条数据,各自分别对应一遍表S2中的各条数据(跟排列组合差不多)不会去掉相同字段。
4、投影
其实是选择某几列的操作
例如:选择表S1中的Sno列和Sname列,Sno,Sname(S1)
也可以用第几列来代表,比如Sno和Sname分别是第1,2列,也可以写作1,2(S1)
5、选择
选择与投影类似,投影选的是列,选择选的是行
例如:选Sno列中的No0003行,Sno=No0003(S1)
也可以用第几列来代表,比如1=No0003(S1)
6、连接
按照两个表的相同字段连接
例如S1和S2中只有Sno字段里的No0001是相同的
则联接可以写为S1.Sno S2.Sno,即按照字段Sno相同的部分联接起来,然后只保留一个相同字段No0001
也可以简写为S1 S2,意思是默认寻找相同字段进行联接
注
连接可分为左联接、右联接、完全外联接
例:
左连接、右连接、完全外连接的结果集数量相同,都是{(2,1,4,8),(3,4,4,4)}
但是元组个数不同,左连接和右连接的元组个数为4个,完全外连接的元组个数为6个.
细节
连接和笛卡尔积
如果想要S1和S2连接后取字段Sno,Sname,Age
应该用投影写作Sno,Sname,Age( S1
S2)或者
1,2,4( S1
S2)
如果想要S1和S2取笛卡尔积后取字段Sno,Sname,Age
应该用投影写作 Sno,Sname,Age( S1xS2)或者
1,2,5( S1xS2)
五、规范化理论
规范化理论的价值与用途
不够规范的数据表中可能存在数据重复等问题,造成数据杂乱无章影响后续对数据的一些操作,所以提出规范化理论。
规范化理论的价值和用途就是:解决非规范化的关系模式所带来的数据冗余、更新异常、插入异常、删除异常等问题;
规范化理论 --- 函数依赖
例如:在函数y= 中;
用x可以确定y的值,此时y的值是依赖于x取何值,故称作y依赖于x,可以写作x-->y,即x确定y,此为函数依赖。
部分函数依赖
传递函数依赖
规范化理论 --- 键 
求解候选键
1.画有向图
将关系模式的函数依赖用有向图表示出来
2.入度为0且可遍历全图
寻找入度为0的属性(没有入度),并以该属性集合为起点,尝试遍历全图,若能遍历有向图中的全部节点,则该属性集为候选键。
3.上述两条件无法全部满足时
情况①:
若有向图中没有入度为0的属性,则需要尝试中间节点(既有入度又有出度的节点),用其遍历有向图,若能遍历全图则为候选键;
情况②:
若单个入度为0的属性并不能遍历全图,此时考虑多个入度为0的属性合并形成集合作为候选键。
情况③:
单个入度为0的属性不能遍历有向图则,而此时又没有其他的入度为0的属性,则考虑将同时有入度和出度的属性与入度为0的属性合并形成集合作为候选键;
例题
例1:
答案:A
据给定关系画有向图
据图可知,属性A1入度为0,且从A1出发能遍历全图(如图中红色虚线所示),所以属性A1为候选键。
例1解题思路:
画出有向图,寻找入度为0的属性遍历全图即可解决
例2:
答案:ABCD
据给定关系画有向图
由上图可知,入度为0的属性是ABCD4个属性,但是其中任意一个都无法遍历全图,4个属性合在一起才能遍历全图,因此此题目中的候选码是ABCD四个属性的集合
例2解题思路:
符合上述情况②,用多个入度为0的属性合并作为集合可遍历全图
注:
注意区分(A-->D;B-->D;C-->D) 、( ABC-->D)、(D-->ABC)
例3:
据给定关系画有向图
此有向图中不存在入度为0的属性,所以寻找有入度和出度的属性,即属性A,属性B;
从属性A出发可以遍历全图,从属性B出发也可以遍历全图,因此在此题目中,候选键为,A和B;
例3解题思路:
符合上述情况①,没有入度为0的属性,则需要尝试中间节点(既有入度又有出度的节点),用其遍历有向图。
注:
注意区分 AB 与 A和B ;AB表示的是属性集合AB作为一个候选键;而A和B表示属性A和属性B都是候选键;
例4:
据给定关系画有向图
老师T可以确定课程J(T-->J);学生S和课程J可以确定老师(SJ-->T);所以得下图
此有向图中入度为0的属性是属性S,属性S并不能独自遍历全图,且没有其他入度为0的属性,所以寻找既有入度又有出度的属性并入入度为0的属性中作为合集遍历全图;
属性T和属性J均是既有入度又有出度的属性,
属性ST结合:T可指向J,可以遍历全图,所以SJ是候选键;
属性SJ结合:SJ指向T已经遍历完全图,所以ST是候选键;
例4解题思路:
符合上述情况③,单个入度为0的属性不能遍历有向图则,而此时又没有其他的入度为0的属性,则考虑将同时有入度和出度的属性与入度为0的属性合并形成集合作为候选键;
注:
此类寻找候选键的题目中,极易出现同时存在多个候选键的情况,若时间充裕注意仔细寻找
六、规范化理论--范式
第一范式(1NF)
在关系模式R中,当且仅当所有域只包含原子值,即每个分量都是不可再分的数据项,则称R是第一范式。
可理解为在一张数据表中,当列名(属性)不可拆分时则称此表是第一范式。
例如:
姓名 | |
个人信息 | |
张三 | 手机号:xxxxx,年龄23 |
王五 | 手机号:xxxxx,年龄25 |
上表中列个人信息可拆分为手机号、年龄两列,所以不是第一范式;
改为第一范式应是:
姓名 | 手机号 | 年龄 |
张三 | xxxxx | 23 |
王五 | xxxxx | 25 |
上表中每一列都不能再拆分,故此表为第一范式。
第一范式的重点:
确保原子性,即每一列数据都不能再拆分。
第二范式(2NF)
当且仅当关系R已经是第一范式时,且每一个非主属性完全依赖主键(即不存在部分依赖)时,则称关系R是第二范式。
主键可以由多个主属性构成,也可以由单一主属性构成。
可以理解为:当一张表已经是第一范式,且非主属性只能由全部主键推出,不可以由部分主键推出时满足第二范式要求。
例如:
学号(SNO) | 课程号(CNO) | 成绩(GRADE) | 学分(CREDIT) |
S01 | C01 | 75 | 4 |
S02 | C01 | 92 | 4 |
S03 | C01 | 87 | 4 |
S04 | C01 | 55 | 4 |
S01 | C02 | 87 | 2 |
S02 | C02 | 95 | 2 |
S01 | C03 | 94 | 5 |
...... | ...... | ...... |
上表中,每一列都不能再拆分,所以此表满足第一范式,(一个学生可以选多个课程,因此学号和课程号单独一个都无法确定成绩,必须二者合起来才能确定学生成绩,所以2个红色属性合并称为一个主键),由主键中的部分属性课程号可以直接确定学分,所以非主属性学分是部分依赖主键,所以上表中存在部分依赖,不满足第二范式;
表中存在问题:
数据冗余:
课程C01对应的学分是4分在表中多次出现;
更新异常:
如果数据多次重复存在,在更新时极易漏更;
插入异常:
如果想要插入新的课程C05学分是6分,但此课程并没有学生选,所以对应的学生学号不存在,但是学号(SNO)是主键,想要插入数据主键不能为0,所以无法插入此课程;
删除异常:
如果此表中的学生已经全部毕业,可以删除他们的成绩,但是学校每届的课程和课程的学分是不变的,此时如果删除成绩,其他属性可能会被连带删除;
改为第二范式应该是:
将表进行提取,分成2个表;
表1:表1中的非主属性完全依赖主键,不存在部分依赖,所以满足第二范式
学号(SNO) | 课程号(CNO) | 成绩(GRADE) |
S01 | C01 | 75 |
S02 | C01 | 92 |
S03 | C01 | 87 |
S04 | C01 | 55 |
S01 | C02 | 87 |
S02 | C02 | 95 |
S01 | C03 | 94 |
...... | ...... | ...... |
表2: 主键由一个属性构成,不存在部分主键,因此也就不存在部份依赖,所以满足第二范式。
所以如果表满足第一范式,且表中的主键只有一个属性的情况下此表满足第二范式。
课程号(CNO) | 学分(CREDIT) |
C01 | 4 |
C01 | 4 |
C01 | 4 |
C01 | 4 |
C02 | 2 |
C02 | 2 |
C03 | 5 |
...... |
而进一步可将表2简化为
课程号(CNO) | 学分(CREDIT) |
C01 | 4 |
C02 | 2 |
C03 | 5 |
...... |
可以解决掉部分: 数据冗余,更新异常,插入异常,删除异常等问题。
第二范式的重点:
确保唯一性,即一张表叙述一件事,例如表1只表述学生的课程成绩,表2只表述课程的学分。
第三范式(3NF)
当且仅当关系R已经满足第一范式和第二范式时,且表中没有非主属性传递依赖于主键时,则称关系R满足第三范式。
可以理解为:一个表满足第一、二范式的情况下,如果表中的非主键可以直接依赖于主键,而不是传递依赖于主键时,此表满足第三范式。
例如:
学号(SNO) | 姓名(SName) | 系号(DNO) | 系名(DNAME) | 系住址(LOCATION) |
S01 | 张三 | D01 | 计算机系 | 1号楼 |
S02 | 李四 | D01 | 计算机系 | 1号楼 |
S03 | 王五 | D01 | 计算机系 | 1号楼 |
S04 | 赵六 | D02 | 信息系 | 2号楼 |
...... | ...... | ...... | ...... | ...... |
上表中,主键是学号(SNO),表中各列不可再拆分满足第一范式,主键是单一属性不存在非主属性部分依赖主键,满足第二范式;
表中,根据学号可以直接推出姓名和系号,但是根据学号无法得到系名和系住址,
只能根据学号推得系号再推得系名,因此系名与学号之间不是直接依赖关系而是间接依赖关系;
据学号推得系号再推得系地址,因此系住址与学号之间不是直接依赖关系而是间接依赖关系;
因此表中非主属性系名,和非主属性系住址,与主键之间都是间接依赖,所以不满足第三范式。
上述表中仍然存在部分: 数据冗余,更新异常,插入异常,删除异常等问题。
改为第三范式应该是:
将表进行提取:分成2个表:
表1:主键是学号,非主属性姓名和系号均直接依赖于主键学号,表中不存在间接依赖关系,因此满足第三范式
学号(SNO) | 姓名(SName) | 系号(DNO) |
S01 | 张三 | D01 |
S02 | 李四 | D01 |
S03 | 王五 | D01 |
S04 | 赵六 | D02 |
...... | ...... | ...... |
表2:主键是系号,非主属性系名和非主属性系住址均直接依赖于主键学号,表中不存在间接依赖关系,满足第三范式。
系号(DNO) | 系名(DNAME) | 系住址(LOCATION) |
D01 | 计算机系 | 1号楼 |
D01 | 计算机系 | 1号楼 |
D01 | 计算机系 | 1号楼 |
D02 | 信息系 | 2号楼 |
...... | ...... | ...... |
而进一步可将表2简化为
系号(DNO) | 系名(DNAME) | 系住址(LOCATION) |
D01 | 计算机系 | 1号楼 |
D02 | 信息系 | 2号楼 |
...... | ...... | ...... |
可以解决掉部分: 数据冗余,更新异常,插入异常,删除异常等问题。
第三范式的重点:
确保独立性,除主键之外,每个属性之间不存在任何形式的依赖,即每个非主属性只完全依赖于主键。
BC范式(BCNF)
BC范式又称巴斯-科德范式或3.5范式,主要是对第三范式的补充,因为第三范式只明确非主属性之间不能存在依关系,并没有明确主键(特指多个属性组成的联合主键)之间不能存在依赖关系,BCNF修正的就是这一点。
上述利用概念区分范式的方式在BCNF中应用起来较难理解(其实主要是因为我不会),所以一般使用如下方法:
BC范式判断方法:
首先满足第一、二、三范式,再用有向图求解候选键(一般此类情况存在多个候选键),依次写出候选键的依赖关系,如果依赖关系的左边均是候选键,则可以确定此关系满足BC范式。
据给定关系画有向图
老师T可以确定课程J(T-->J);学生S和课程J可以确定老师(SJ-->T);所以得下图
此有向图中入度为0的属性是属性S,属性S并不能独自遍历全图,且没有其他入度为0的属性,所以寻找既有入度又有出度的属性并入入度为0的属性中作为合集遍历全图;
属性T和属性J均是既有入度又有出度的属性,
属性ST结合:T可指向J,可以遍历全图,所以SJ是候选键;
属性SJ结合:SJ指向T已经遍历完全图,所以ST是候选键;
每个属性不可再拆分,满足原子性即满足第一范式;
候选键中出现的属性均为主属性,所以此题目中STJ三个属性均为主属性,不存在非主属性。
没有非主属性,即不存在非主属性部分依赖主属性,满足第二范式;
没有非主属性,即不存在非主属性之间存在传递依赖,满足第三范式;
此题目有两个候选键,分别是ST和SJ;而他的依赖关系是T-->J 和 SJ-->T,其中依赖关系T-->J 的左侧不是候选键,所以不满足BC范式依赖关系的左边均是候选键的要求,因此,此关系不满足BC范式。
例题:
此类例目题严格来讲并不完善,存在许多地方并不严谨,做此类题目时最好根据选项判断,从选项中选择相对更正确一些的,或者直接根据选项的思路做排除。
问题(1):
A:部分依赖的只存在于主键(主码)是由多个主属性构成的情况下,题目中并未说明主键是单属性还是多属性,而单属性部门号完全可以做主键,所以当单属性部门号作为主键时,存在的说传递依赖而不是部分函数依赖,故排除。
B:同样在单属性做主码时,不存在部分函数依赖,故排除。
C:在单属性做主码时,已经不存在部份依赖只存在传递依赖,故选择。
D:同样在单属性做主码时,不存在部分函数依赖,故排除。
问题(2):
此空与问题(3)相关联,而(3)的选项中添加的是销售,即(2)中需要完善的只有职工号、部门号、姓名。因此可以排除BC,部门实体与职工实体之间是一对多的关系,联系E-R图,一般会将少的加在多的一方,所以选D。
问题(3):.
选项中可以确定是需要添加销售关系,第一项是职工号,问题(2)结束后,职工号已经可以确定部门名了,所以为了避免冗余,二者保留其一,故排除CD,而选项B中,商品号和商品名二者存在冗余,所以二者选其一就可,故选A。
联系
简记
属性不可分割是第一范式
存在传递依赖是第二范式
不存在非主属性传递依赖是第三范式
关系数据库设计理论主要包括数据依赖、范式、关系模式三个方面,其中数据依赖为核心。
反规范化
规范化是为了减少数据的冗余提高增、删、改的速度,但是由于表不断被拆分,导致表的数量过多增加了查询的工作量,系统需要进行多次连接才能进行查询操作,使得系统效率下降,因此提出反会反规范化理论。
反规范化理论的操作过程:
增加派生性冗余列、增加冗余列、重新组表、分割表。
七、规范化理论--模式分解
保持函数依赖分解
将一个关系模式按函数依赖进行分解,分解后该模式的函数依赖仍然成立。
例如:
关系内不存在冗余
关系R(A,B,C)中,有A、B、C三个属性
依赖关系是:A-->B ; B-->C;
如果划分为 R1(A,B);R2(B,C)则称之为保持函数依赖划分;
关系内存在冗余
关系R(A,B,C)中,有A、B、C三个属性
依赖关系是:A-->B ; B-->C ; A-->C;
由A-->B ; B-->C ;可知A-->C;所以A-->C;是关系冗余
如果划分为 R1(A,B);R2(B,C)则依然称之为保持函数依赖划分;
有损、无损分解
有损分解:
是不能还原的,例如将一张照片压缩为jpg格式,此时放大看照片会模糊,这便是有损压缩;
无损分解:
是可以还原的,例如将文件压缩成压缩包,然后解压之后还能得到原来的文件,这便是无损分解;
无损联接分解:
将一个关系模式分解成若干个关系模式之后,通过自然联接和投影等运算仍能还原到原来的关系模式。
例:
有关系模式
成绩(学号,姓名,课程号,课程名,分数);
函数依赖:学号→姓名,课程号→课程名,(学号,课程号)→分数
若将其分解为
成绩(学号,课程号,分数)
学生(学号,姓名)
课程(课程号,课程名)
思考此分解是否为无损分解
思路:
由于关系:学号→姓名,可以将两个带有学号属性的关系进行连接
成绩(学号,课程号,分数) 联接 学生(学号,姓名)
得到 成绩(学号,课程号,分数,姓名)
由于关系:课程号→课程名,可以将两个带有课程号属性的关系进行连接
成绩(学号,课程号,分数,姓名)联接 课程(课程号,课程名)
得到 成绩(学号,姓名,课程号,课程名,分数)即可以恢复到原来关系
方法一:列表
首行表示原有关系 成绩(学号,姓名,课程号,课程名,分数)
下面三行分别表示原有关系分成了成绩、学生、课程三个子关系
a表示在此行对应的子关系中存在该属性;b表示在此子关系中对应的属性不存在,a的下标是列号,b的下标是行号列号。
例如:成绩行中的内容表示子关系成绩(学号,课程号,分数)
根据成绩(学号,课程号,分数)关系 联接 学生(学号,姓名)关系
得到 成绩(学号,课程号,分数,姓名)
如下图所示:
再根据上述成绩(学号,课程号,分数,姓名)联接 课程(课程号,课程名)
得到 成绩(学号,姓名,课程号,课程名,分数)如下图所示:
由上图可知,成绩一行已经全部为a,即代表可以恢复到原来关系,即本次分解为无损分解。
方法二:计算
此方法十分高效但是具有很强的局限性,只能用于将一个关系一分为二,一分为三则不适用。
例题
题目意思是,有关系R中存在三个属性A、B、C;将这三个属性分别按照ρ1,ρ2两种方法进行分解,ρ1中将其分为R1,R2两个关系R1中包含属性A、B;R2中包含属性A、C;
按照上述定理
分解方式ρ1
R1∩R2=A;R1-R2=B;R2-R1=C;
R1∩R2 → (R1-R2) = A→B(得到依赖关系A→B);
R1∩R2 → (R2-R1) = A→C(得到依赖关系A→C);
依赖关系A→B与A→C只要能有一个在题目给定得原始关系中存在过则说明是无损分解。
依赖关系A→B与A→C能够对应题目中的A→B,因此分解方式ρ1是无损分解
同理分解方式ρ2
R1∩R3=B;R1-R3=A;R3-R1=C;
R1∩R3 → (R1-R3) = B→A(得到依赖关系 B→A);
R1∩R3 → (R3-R1) = B→C(得到依赖关系B→C);
依赖关系B→A与B→C只要能有一个在题目给定得原始关系中存在过则说明是无损分解。
依赖关系B→A与B→C均无法对应题目中的A→B因此分解方法ρ2不是无损分解是有损分解。
八、数据库并发控制
事务
将多项存在关联性操作进行封装,看作一个整体再对其进行操作,此整体叫做事务,事务拥有4个特性:以银行转账为例
原子性:
要么都做,要么都不做。
例如: 银行转账过程中,动作1:从A卡里扣除钱;动作2:将钱打入B卡里;如果进行转账操作,则两个动作都需要做,如果不做就都不能做,否则会出现错误问题,即将两个动作看作不可分割的整体此为原子性。
一致性:
事务开始前和结束后,数据库的完整性约束没被破坏。
银行转账前,A卡和B卡一共有多少钱,转账之后依然应该是多少钱,只不过是发生了钱数的转移,操作前后整体是一致的,类似于能量守恒定律,此为一致性。
隔离性:
事务之间是独立进行的,隔离的,互不影响。
持续性:
事务结束前,所有数据改动必须保持到物理存储中,即使数据库崩溃,其对数据库的更新操作的结果也不会丢失。
事务执行之后他的结果的影响是持续的,例如转账之后A卡里永远少了钱,B卡里永远多了钱。
并发操作
可以理解为:并发操作是指多项事务同时对数据进行操作,但数据一次只能对接一个事务的操作,例如数据一次只应对一个事务的读取,所以多个事务的读取要分先后顺序,写入也要分先后顺序,因此并发操作会产生一系列的问题:
丢失更新:
第④步写回的结果会覆盖第③步写回的结果,因此最终的结果是A=2,事务1更新的结果丢失
事务1 | 事务2 |
①读A=10 | |
②读A=10 | |
③A=A-5写回 | |
④A=A-8写 |
不可重复读问题:
事务1中对AB进行求和,然后为保证准确性会二次读入进行验算,但第二次读入的数据A是事务2写回的结果,所以事务1会出现错误。
事务1 | 事务2 |
①读A=20 读B=30 求和=50 | |
②读A=20 A=A+50 写回=50 | |
③读A=70 读B=30 求和=100 (验算错误) |
脏数据的读出:
脏数据并不是实质产生的数据,只是执行过程中临时出现的数据。
事务1 | 事务2 |
①读A=20 A=A+50 写回70 | |
②读A=70 | |
③ROLLBACL(回滚恢复原值) A恢复为20 |
一级封锁协议
在事务T修改数据R之前必须先对其加X锁(写锁),直到事务结束才释放,可以防止丢失修改。
例如:
丢失更新中,在事务1修改数据A=10之前加X锁,直到事务1结束后再释放;在释放之前事务2都不能修改数据A的值。
二级封锁协议
在一级封锁协议的基础之上,读取数据R之前加S锁(读锁);读完之后即可释放S锁,可防止丢失修改,还可防止读到脏数据。
例如:
丢失更新中,在事务1读取A=10之前加S锁,事务1读取A=10之后再释放;在释放之前事务2都不能读取数据A的值。
对于同一数据,读锁之上还能加读锁,写锁之上不能加任何锁;
三级封锁协议
一级封锁协议加上事务T在读取数据R之前先对其加S锁,直到事务结束才释放。可防止丢失修改、放置读脏数据、防止数据重复读取。
例如:
丢失更新中,在事务1读取A=10之前加S锁,事务1完全结束之后再释放;在释放之前事务2都不能读取数据A的值。
两段锁协议
两段锁协议最大的特点是可串行化,可能发生死锁,死锁可预防可解除。
九、数据库完整性约束、数据库安全
实体完整性约束
实体完整性约束是针对表中的主键来说的,即数据表中必须定义主键,主键内容不能为空,不能重复。
参照完整性约束
参照完整性约束是针对外键
例如:
员工(员工号,姓名,性别,部门号);部门(部门号,部门名,人数)
员工表内存在外键部门号,此时员工表中的部门号不能随便乱填,只能是部门表中的部门号对应的数字,允许为空值。
用户自定义完整性
用户自定义完整性是用户自己设定的规则。
例如:
一张表中的某列是年龄,那么用户可以自定义该列的数值范围是0-200之,一旦输入的数值为负数或者是超出200,就会报错。
触发器
上述三种完整性约束只适用于比较简单,单一的情况下,如果表中有更复杂的要求一般使用触发器编写脚本来实现表格中的约束条件。
数据库安全
数据库安全包含以下几种措施。
用户标识和鉴定
用户标识和鉴定是最外城的安全保护措施,可以使用用户账户登录及密码、口令及随机数检验等方式。
存取控制
对用户进行授权,不同的用户可以授予不同的权限,包括操作类型(增、删、改、查等动作),和数据对象(数据范围)等。
密码存储和传输
对远程的终端可以进行加密传输
视图的保护
对视图进行授权,对不同的用户开放不同的权限。
审计
审计是一种事后的记录,使用一个专用文件或者数据库,自动将用户对数据库的所有操作以日志的方式记录下来。
存储过程
一组可以完成特定功能的SQL数据集,储存在数据库中,一次编译永久有效。在更新数据时供第三方调用,避免向第三方提供系统的表结构,保证数据安全。
十、数据的备份与恢复
按照备份方式划分
冷备份
又称静态备份,是将数据库正常关闭,停止工作,在静止状态下,将数据库的文件全部复制下来。
优点 | 缺点 |
备份只需要复制文件备份速度非常快 容易归档(简单复制即可) 容易恢复到某个时间点上(只需将文件复制回去) 能与归档方法相结合,做数据库最佳状态的恢复,低度维护高度安全 | 单独使用时,只能提供到某一时间点上的恢复 在备份时数据库完全停止其他工作只做备份 若磁盘空间有限只能恢复到其他外部储存设备上,速度很慢 由于是直接按照文件复制,不能按照表或者用户恢复 |
热备份
又称动态备份,利用备份软件,在数据库正常运行的状态下,将数据库中的数据文件备份出来。
优点 | 缺点 |
可以直接在表空间或数据库文件级别上备份 备份时间短 备份时数据库仍可正常使用 可达到秒级恢复(恢复到某一时间点) 可对几乎所有数据库实体做恢复 恢复速度快 | 备份时数据库正常运行,出错的后果非常严重 若备份不成功所得的结果不可用于时间点的恢复 维护困难 |
按照备份范围划分
完全备份
备份所有的数据
差量备份
仅备份上一次完全备份之后变化的数据
增量备份
备份上一次备份之后变化的数据
周日 | 周一 | 周二 | 周三 | 周四 | 周五 | 周六 |
完全备份 | 增量备份 | 增量备份 | 增量备份 | 差量备份 | 增量备份 | 增量备份 |
增量备份的范围:上次备份后到目前的变化的数据;
差量备份的范围:上次完全备份之后到目前变化的数据;
上表中
周日完全备份后,
周一是增量备份周日完全备份后到周一备份前的数据;
周二是增量备份周一增量备份后到周二增量备份前的数据;
周三是增量备份周二增量备份后到周三增量备份前的数据;
周四差量备份是备份周日完全备份后到周四差量备份前的数据;
若想要恢复周三的数据需要先将周日完全备份的数据恢复,再将周一、周二增量备份的数据恢复然后才能恢复周三增量备份的数据,因此增量备份备份数据量小,但是恢复起来比较麻烦。
若想要恢复周四的数据则可以先恢复周日的完全备份数据,再直接恢复周四差量备份的数据即可,备份数据量大,但是恢复较为容易。
增量备份和差量备份一般是结合使用来应对不同需求。
其他方式
转储其实就是备份
静态海量转储
在系统中无运行事务时进行,每次转储全部数据。
静态增量转储
在系统中无运行事务时进行,每次只转储上一次转储后更新的数据。
动态海量转储
转储期间允许对数据库进行存取或修改,每次转储全部数据库。
动态增量转储
转储期间允许对数据库进行存取或修改,每次只转储上次转储后更新过的数据。
日志文件
事务日志是针对数据库改变所做的记录,记录针对数据库所做的任何操作,并将记录结果保存在独立文件中。
用途
例如在此表中
周日 | 周一 | 周二 | 周三 | 周四 | 周五 | 周六 |
完全备份 | 增量备份 | 增量备份 | 增量备份 | 差量备份 | 增量备份 | 增量备份 |
上表中的数据一天才进行一次备份,无论是何种形式的备份,都无法在数据库更新后进行实时备份,也就是说如果数据库在上一次备份后,下一次备份前发生问题,只依靠每天一次的备份来恢复的数据是不完整的,而日志文件可以将针对数据库所做的任何操作记录下来形成文件,正好可以弥补空缺。
数据库的故障与恢复
故障关系 | 故障原因 | 解决方法 |
事务本身可以预期的故障 | 本身逻辑存在问题 | 在程序中预先设置ROLLBACK(回滚)语句用来回退恢复数据 |
事务本身的不可预期故障 | 算数溢出、违反存储保护 | 由DBMS的恢复子系统通过日志,撤销事务对数据库的修改,退回初始状态 |
系统故障 | 系统停止运转 | 检查点法 |
介质故障 | 外存损坏 | 使用日志重做业务 |
十一、 数据仓库与数据挖掘
数据仓库和数据库的区别
数据库
数据库是根据应用程序的业务需求,记录下来的该应用程序业务所需要的数据,数据库往往与应用程序相辅相成,需要频繁的与应用程序进行交互(增、删、改、查)等。
例如:
超市收银系统通过扫描条码就可以从数据库中查找出该条码对应的商品与该商品的相关信息。
数据仓库
数据仓库是累积下来的大量数据,一般不会存在频繁交互,基本上是累积下来就不再改动了。
例如:
超市收银系统每出售一样商品都会扫描,扫描累积下来的数据可以作为数据仓库进行收存,然后通过数据分析可以得出热销商品等信息。
数据仓库特点
面向主题:
将关于主题的数据组织起来分析数据之间的关系,即根据主题进行数据分析,例如我想要找寻哪个时段冰淇淋销售最多,我就以冰激凌销量作为主题从数据仓库中进行查询。
集成的:
将与主题相关的数据集中起来对数据进行一系列预处理,记录集成式数据,例如将超市的日报表、周报表、月报表进行存储。
相对稳定性(非易失)
数据仓库中进入的数据不再做增删改查等操作,相对来说比较稳定
反映历史变化(随着时间变化)
隔段时间会导入新的数据,长期累积可以反映数据随时间的变化情况
数据仓库建立流程
数据源可能由多种来源,格式不一,所以从中抽取数据之后要进行数据清理,将其格式统一取出冗余,然后装载入数据仓库进行刷新。
直接建立大的数据仓库风险比较高,所以分成许多部分一步步构成最后组合,所分成的许多部分称之为数据集市。
OLAP服务器是连接分析服务器,将最表层前端工具与数据仓库进行连接。
数据挖掘
数据挖掘是指从数据仓库中挖掘出某一主题的相关情况。往往是不能直接查询到的,例如想要挖掘某饮料在某段时间的销售量,根据挖掘结果调整销售量达到利益最大化。
数据挖掘方法
决策树
神经网络
遗传算法
关联规则挖掘算法
数据挖掘分类
关联分析
挖掘出隐藏在数据间的相互关系。
序列模式分析
侧重点是分析数据间的前后联系(因果关系)
分类分析
为每一个记录赋予一个标记再按标记分类
聚类分析
分类分析法的逆过程
分布式数据库基础
分布式数据系统由传统的数据库发展而来,同样具有集中控制的特性。
分布式数据库中的数据一般存储在经常使用的场地上,因而同一数据可能重复存放在两个场地上,但是这种冗余是在系统控制下的,因此系统具有数据冗余的可控性。
透明性
逻辑透明性 | 用户不必关心DBMS支持哪种数据类型,使用哪种操纵语言,其中的转换由系统完成 |
位置透明性 | 用户不必知道操作的数据放在何处 |
分片透明性 | 用户不必关心数据是如何分片存储的 |
复制透明性 | 用户无需知道数据是复制到哪些节点,如何复制的 |
特性
共享性 | 数据存放在不同的节点,可以共享 |
自治性 | 每个节点可独立管理本地数据 |
可用性 | 某一副本故障,还能使用其他部分保证分布式数据库系统运行 |
分布性 | 数据存储可分别存放在不同节点 |
十二、大数据基本概念
大数据技术其实就是对海量的数据进行处理的一些技术,要求处理速度极快、数据具有多样性并且具有一定的价值。
传统数据与大数据的区别
传统数据 | 大数据 | |
数据量更大 | GB或TB级 | PB级别或以上 |
数据分析需求更多 | 现有的数据分析与检测 | 深度分析拓展(关联分析、回归分析) |
硬件平台不同 | 高端服务器 | 集群平台 |
大数据处理系统应该具有的重要特征
高度可扩展性(集群可满足)
高性能(集群可满足)
高容错(集群可满足)
支持异构环境(性能高分析快)
较短的分析延迟(分析速度快)
易用且开放的接口
较低成本
向下兼容性
完整性约束条件
主键:PRIMARY KEY
候选键:UNIQUE
外键:FOREIGN KEY(属性) REFERENCES(外键属性,通常为外来主键)
不为空:NOT NULL
取值唯一:NOT NULL UNIQUE
常用语句
创建表
create table<表名>(<列名><数据类型>[完整性约束条件]
<列名><数据类型>[完整性约束条件]
<列名><数据类型>[完整性约束条件]
....... );
修改表
alert table<表名>[add<新列名><数据类型>[完整性约束条件]]
drop<完整性约束>
[modify<列名><数据类型>];
删除表
drop table<表名>;
创建索引
create [unique] [cluster] index<索引名>
on<表名>(<列名>[<次序>][<列名><次序>]].....)
注:次序一般为升序ASC,降序DSC
删除索引
drop index<索引名>;
创建视图
create view 视图名(列表名)
as select 查询子句(可以是任何复杂子句,但不能含有opder by 和distinct)
[with check option];(表示操作时保证更新)
删除视图
drop view 视图名
数据查询
select [all | distinct]<目标列表达式>[,<目标列表达式>]...
from <表名或视图名>[,<表名或视图名>]
[where <条件表达式>]
[group by <列名1>[having]<条件表达式>]]
[order by <列名2>[ASC|DESC]...];
数据更新
插入
inster into 基本表名 [(字段名[,字段名...])]
value(常量[,常量]);
inster into 基本表名 [(字段名[,字段名...])]
select 查询语句;
删除
delect from 基本表名
[where 条件表达式];
修改
update 基本表名
set 列名=值表达式[,列名=值表达式...]
[where 条件表达式];
授权
grant <权限>[,<权限>]...
[on<对象类型><对象名>]
to<用户>[<,用户>]...
[with grant option];
收回权限
fevoke <权限>[,<权限>]...[on<对象类型><对象名>]
from <用户>[<,用户>]...
创建函数
cerat function 函数名(参数名 参数类型)
returns 返回值类型
as
begin
函数体
declare 变量名 变量类型
...
return 表达式
end