一、數據庫設計范式及其意義和不足
數據庫的設計范式是數據庫設計所需要滿足的規范,數據庫的規范化是優化表的結構和優化把數據組織到表中的方式,這樣使數據更明確,更簡潔。實踐中,通常把一個數據庫分成兩個或多個表並定義表之間的關系以做到數據隔離,添加、刪除和修改某個字段只需要在一個表中進行,接着可以通過定義的關系傳遞到數據庫中剩余的表中(和分層思想的意義所在很相似)。這樣我們可以消除很多錯誤或垃圾數據出現的機會並減輕更新信息所必要的工作量。
目前,主要有六種范式:第一范式、第二范式、第三范式、BC范式、第四范式和第五范式。滿足最低要求的叫第一范式,簡稱1NF。在第一范式基礎上進一步滿足一些要求的為第二范式,簡稱2NF。其余依此類推
事物往往具有多面性,設計范式也會帶來一定的麻煩:操作困難,因為需要聯系多個表才能得到所需要數據,而且范式越高性能就會越差。所以使用多高的范式需要權衡利弊,一般在項目中,使用到第三范式也就足夠了,性能好而且方便管理數據。
二、下面我們來舉例介紹一下數據庫設計三范式
說明:實例采用《學校機房收費系統》的“學生信息表”,“學生上下機記錄表”的部分字段
1、第一范式1NF
定義:數據庫表中的字段都是單一屬性的,不可再分。
簡單的說,每一個屬性都是原子項,不可分割。
1NF是關系模式應具備的最起碼的條件,如果數據庫設計不能滿足第一范式,就不稱為關系型數據庫。也就是說,只要是關系型數據庫,就一定滿足第一范式。
我們先來看一張不符合1NF的表1-1
CardNo |
StudentNo |
StudentName |
Sex |
Department |
CardCash |
UserID |
UserLevel |
Time |
001 |
021101 |
小明 |
男 |
教育學院,心理系,1班 |
100 |
Operator |
操作員 |
2011/10/03,09:00 |
之所以說這張表不符合1NF,是因為Department和Time字段可以再分,所以應該更改為表1-2:
CardNo |
StudentNo |
StudentName |
Sex |
Academy |
Major |
class |
CardCash |
UserID |
UserLevel |
Date |
Time |
001 |
021101 |
小明 |
男 |
教育學院 |
心理系 |
1 |
100 |
Operator |
操作員 |
2011/10/03 |
09:00 |
2、第二范式2NF
定義:數據庫表中不存在非關鍵字段對任一候選關鍵字段的部分函數依賴,即符合第二范式。
《注:什么是函數依賴,詳見百度百科(http://baike.baidu.com/view/40008.htm)。
如果一個表中某一個字段A的值是由另外一個字段或一組字段B的值來確定的,就稱為A函數依賴於B。》
2NF可以減少插入異常,刪除異常和修改異常。
簡單的說,一方面,第二范式肯定要滿足第一范式,否則就沒有必要談第二范式。
另一方面,當某張表中的非主鍵信息不是由整個主鍵函數來決定時,即存在依賴於該表中不是主鍵的部分或者依賴於主鍵一部分的部分時,通常會違反2NF。
我們再來看上面的滿足1NF的表1-2
CardNo |
StudentNo |
StudentName |
Sex |
Academy |
Major |
class |
CardCash |
UserID |
UserLevel |
Date |
Time |
001 |
021101 |
小明 |
男 |
教育學院 |
心理系 |
1 |
100 |
Operator |
操作員 |
2011/10/03 |
09:00 |
我們看到,在這張表中,通過CardNo和StudentNo就可以確定StudentName,Sex,Academy,Major,class,CardCash,UserID,Date,Time。所以可以把CardNo和StudentNo的組合作為主鍵。
但是,我們發現CardCash並不完全依賴於CardNo和StudentNo,僅僅通過CardNo就可以確定CardCash,因為一張卡,一定會有卡內金額。這就造成了部分依賴。出現這種情況,就不滿足第二范式。
修改為:
我們再來看另一個例子,學生上下機記錄表,會更明顯些。表2-1
CardNo |
StudentNo |
StudentName |
Sex |
Department |
Major |
class |
OnDate |
OnTime |
OffDate |
OffTime |
ConsumeTime |
ConsumeMoney |
001 |
0211 |
小明 |
男 |
教育學院 |
心理系 |
1 |
2011/10/14 |
09:00 |
2011/10/14 |
10:00 |
1 |
2 |
我們看到,在這張表中,StudentName,Sex,Department,Major,class都是直接依賴於StudentNo,而不依賴與表中的其他字段,這樣的設計也不符合2NF非主鍵信息不是由整個主鍵函數來決定時。
我們可以把1-2和2-1優化為:
3-1
StudentNo |
CardNo |
UserID |
UserLevel |
Date |
Time |
021101 |
001 |
Operator |
操作員 |
2011/10/03 |
09:00 |
3-2
CardNo |
CardCash |
001 |
98 |
3-3
CardNo |
OnDate |
OnTime |
OffDate |
OffTime |
ConsumeTime |
ConsumeMoney |
001 |
2011/10/14 |
09:00 |
2011/10/14 |
10:00 |
1 |
2 |
3-4
StudentNo |
StudentName |
Sex |
Academy |
Major |
class |
021101 |
小明 |
男 |
教育學院 |
心理系 |
1 |
3、第三范式3NF
定義:在第二范式的基礎上,數據表中如果不存在非關鍵字段對任一候選關鍵字段的傳遞函數依賴則符合3NF。
我們來看上例中優化后的表3-1
StudentNo |
CardNo |
UserID |
UserLevel |
Date |
Time |
021101 |
001 |
Operator |
操作員 |
2011/10/03 |
09:00 |
在表中,一個UserID能確定一個UserLevel。這樣,UserID依賴於StudentNo和CardNo,而UserLevel又依賴於UserID,這就導致了傳遞依賴,3NF就是消除這種依賴。
我們把3-1進行優化得到:
4-1
StudentNo |
CardNo |
UserID |
Date |
Time |
021101 |
001 |
Operator |
2011/10/03 |
09:00 |
4-2
UserID |
UserLevel |
Operator |
操作員 |
我們看到,第三范式規則查找以消除沒有直接依賴於第一范式和第二范式形成的表的主鍵的屬性。我們為沒有與表的主鍵關聯的所有信息建立了一張新表。每張新表保存了來自源表的信息和它們所依賴的主鍵。
三、總結
數據庫設計規范化能讓我們更好地適應變化,使你能夠改變業務規則、需求和數據而不需要重新構造整個系統。
規