模式分解保持函数依赖判断——数据库考试复习
已知R<U,F>,U={A,B,C,D,E},F={A—>C,B—>C,C—>D,DE—>C,CE—>A},R的一个分解为R1(AD),R2(AB),R3(BE),R4(CDE),R5(AE),判断这个分解是否具有函数依赖性。分解出的R1 F1{A—>D} R2 F2{Q} R3 F3{Q},R4(CDE) F4(DE->C,C->D}A
前言
定义1:设R(U,F)是一个关系模式,F是函数依赖集,若F
+
^+
+= (
U
U
U
i
=
1
k
F
i
)
_{i=1}^{k}F_i)
i=1kFi)
+
^+
+,则R<U, F>的分解ρ={ R1<U1, F1>,R2<U2, F2>,…,Rk<Uk, Fk> } ,则分解ρ保持函数依赖。
定义2:分解前函数依赖的闭包和分解后各个函数依赖并集的闭包相等;即分解不能丢失函数依赖
保持函数依赖性判断完全可以根据定义及Armstrong公理进行判断。对于不能简单的推算出是否保持函数依赖,则需要通过以下算法实现。
判断算法
判断一个模式分解是否保持函数依赖,假设R(U,F)分解为R1(U1,F1)、R2(U2,F2)… R
n
_n
n(U
n
_n
n,F
n
_n
n)
其中:U
1
_1
1
∪
∪
∪U
2
_2
2…
∪
∪
∪U
n
_n
n=U,F
1
_1
1、F
2
_2
2、F
n
_n
n分别是F在U
1
_1
1、U
2
_2
2…U
n
_n
n上的投影。处理步骤如:
第一步:设F’=F
1
_1
1UF
2
_2
2…UF
n
_n
n;判断F’是否覆盖了F,若包含了F中所有的函数依赖,则一定是保持函数依赖的,判断结束,否则进入第二步
第二步:对F’中没显式包含的函数依赖依据armstrong公理做初步判断,F’蕴含了该函数依赖,F’覆盖了该函数依赖。如不能判断得出,使用以下算法去实现,只要有一个函数依赖没有覆盖的到,则不保持函数依赖。是否蕴含了某个函数依赖判断的算法如下:
假设:需要判断是否蕴含了
α
α
α->
β
β
β函数依赖;
令 Result=
α
α
α
开始扫描R
i
_i
i,T=(Result
∩
R
∩R
∩R
i
_i
i)
F
+
_F^+
F+∩Ri
令:Result=Result
∪
∪
∪T
Result包含了
β
β
β,则:
α
α
α->
β
β
β成立,算法终止
Result有变化,但还没包含
β
β
β,继续下一轮
Result无变化,且不包含
β
β
β,则:
α
α
α->
β
β
β不成立,分解不覆盖
α
α
α->
β
β
β,说明不保持函数依赖。
示例
例1:已知R<U,F>,U={A,B,C,D,E},F={A—>C,B—>C,C—>D,DE—>C,CE—>A},
R的一个分解为R1(AD),R2(AB),R3(BE),R4(CDE),R5(AE),判断这个分解是否具有函数依赖性。
解:
求投影:R
1
_1
1 F
1
_1
1{A—>D} ,R
2
_2
2 F
2
_2
2{
Ø
Ø
Ø} ,R
3
_3
3 F
3
_3
3{
Ø
Ø
Ø},R
4
_4
4(CDE), F
4
_4
4(DE->C,C->D}
F’=F
−
-
−(F
1
_1
1UF
2
_2
2UF
3
_3
3UF
4
_4
4)={A->D、DE->C,C->D}
A->C、B->C、CE->A这些函数依赖需要进一步的判断是否被覆盖到
根据Armstrong公理简单判断不出,F’是否蕴含了A->C、B->C、CE->A等函数依赖
转入求闭包操作:
A->C:
第一轮:
令: Result={A}
Result与R1求交,为{A}, 求A的闭包:A
F
+
_F^+
F+={ACD}, 则T={ACD}
∩
∩
∩R
1
_1
1={AD}; Result= Result
∪
∪
∪T={AD}
Result与R2求交,为{A}, 求A的闭包:A
F
+
_F^+
F+={ACD}, 则T={ACD}
∩
∩
∩R
2
_2
2={A}; Result= Result
∪
∪
∪T={AD}
Result与R3求交,为{
Ø
Ø
Ø}, Result= Result
∪
∪
∪T={AD}
Result与R4求交,为{D}, 求D的闭包:D
F
+
_F^+
F+={D}, 则T={D}
∩
∩
∩R
4
_4
4={D} Result= Result
∪
∪
∪T={AD}
Result与R5求交,为{A}, 求A的闭包:A
F
+
_F^+
F+={ACD}, 则T={ACD}
∩
∩
∩R
5
_5
5={A} Result= Result
∪
∪
∪T={AD}
第一轮,开始Result={A},最后得到Result={AD},Result发生变化,开始第二轮
第二轮
此时, Result={AD}
Result与R1求交,为{AD}, 求AD的闭包:AD
F
+
_F^+
F+={ACD}, 则T={ACD}
∩
∩
∩R
1
_1
1={AD}; Result= Result
∪
∪
∪T={AD}
Result与R2求交,为{A}, 求A的闭包:A
F
+
_F^+
F+={ACD}, 则T={ACD}
∩
∩
∩R
2
_2
2={A}; Result= Result
∪
∪
∪T={AD}
Result与R3求交,为{
Ø
Ø
Ø}, Result= Result
∪
∪
∪T={AD}
Result与R4求交,为{D}, 求D的闭包:D
F
+
_F^+
F+={D}, 则T={D}
∩
∩
∩R
4
_4
4={D} Result= Result
∪
∪
∪T={AD}
Result与R5求交,为{A}, 求A的闭包:A
F
+
_F^+
F+={ACD}, 则T={ACD}
∩
∩
∩R
5
_5
5={A} Result= Result
∪
∪
∪T={AD}
第二轮,开始Result={AD},最后得到Result={AD},Result无变化且Result不包含C,不能覆盖A->C,无需做其他两个验证了。
所以:此模式分解不保持函数依赖性。
例2:给定关系模式R(U,F),U={A,B,C,D} F={A->B, B->C, C->D, D->A}
分解为R1:{AB}、R2{BC}、R3{CD},判断此分解是否具有依赖保持性
解:求投影
R
1
_1
1 F
1
_1
1{A->B,B->A} ,
R
2
_2
2 F
2
_2
2{C->B,B->C} ,
R
3
_3
3 F
3
_3
3{C->D,D->C},
F’=(F
1
_1
1UF
2
_2
2UF
3
_3
3UF
4
_4
4)={A->B,B->A,C->B,B->C,C->D,D->C}
缺少: 函数依赖D->A;
D
F
′
+
_F'^+
F′+={DCBA};表示F’蕴含了D->A,F’与F是等价的;所以保持函数依赖性
完毕。
我们可以使用第三步方法再验证一下F’是否蕴含了D->A
第一轮:
令: Result={D}
Result与R1求交,为{
Ø
Ø
Ø}, 求
Ø
Ø
Ø的闭包得到
Ø
Ø
Ø,T={
Ø
Ø
Ø}
∩
∩
∩R
1
_1
1={
Ø
Ø
Ø}; Result= Result
∪
∪
∪T={D}
Result与R2求交,为{
Ø
Ø
Ø}, 求
Ø
Ø
Ø的闭包得到
Ø
Ø
Ø,T={
Ø
Ø
Ø}
∩
∩
∩R
2
_2
2={
Ø
Ø
Ø}; Result = Result
∪
∪
∪T={D}
Result与R3求交,为{D}, 求D的闭包,D
F
+
_F^+
F+={ABCD},T={ABCD}
∩
∩
∩R
3
_3
3={CD}; Result= Result
∪
∪
∪T={CD}
由于最后的Result={CD}和最初的Result={D}不同,我们开始第二轮
第二轮:
Result={CD}
Result与R1(AB)求交,为{
Ø
Ø
Ø}, 求
Ø
Ø
Ø的闭包得到
Ø
Ø
Ø,T={
Ø
Ø
Ø}
∩
∩
∩R
1
_1
1={
Ø
Ø
Ø}; Result= Result
∪
∪
∪T={CD}
Result与R2(BC)求交,为{C}, 求C的闭包C
F
+
_F^+
F+={ABCD},T={ABCD}
∩
∩
∩R
2
_2
2={BC}; Result= Result
∪
∪
∪T={BCD}
Result与R3(CD)求交,为{CD}, 求CD的闭包,DC
F
+
_F^+
F+={ABCD},T={ABCD}
∩
∩
∩R
3
_3
3={CD}; Result= Result
∪
∪
∪T={BCD}
由于最后的Result={BCD}和最初的Result={CD}不同,我们开始第三轮
第三轮:
Result={BCD}
Result与R1(AB)求交,为{B}, 求B的闭包B
F
+
_F^+
F+={ABCD},T={ABCD}
∩
∩
∩R
1
_1
1={AB}; Result= Result
∪
∪
∪T={ABCD}
此时:result已经包含了A,说明F’是否蕴含了D->A
F’与F等价,保持函数依赖性。
结论
保持函数依赖性,就是做模式分解后的F’(各个子模式函数依赖的并集)是否与F(原有的函数依赖集)等价,F’包含所有的F中的函数依赖则可以得出保持函数的依赖性(充分条件),如果F’不显式包含F中的函数依赖,还需进一步判断,判断方法有两条,第一种是通过F’中的属性闭包去求,是否蕴含函数依赖(这种方法要求做函数投影时,不能缺项);第二种使用给定的算法去求,对投影要求简单,但过程特别麻烦。
开放原子开发者工作坊旨在鼓励更多人参与开源活动,与志同道合的开发者们相互交流开发经验、分享开发心得、获取前沿技术趋势。工作坊有多种形式的开发者活动,如meetup、训练营等,主打技术交流,干货满满,真诚地邀请各位开发者共同参与!
更多推荐
所有评论(0)