表格为第3范式,但有明显的冗余

时间:2015-08-30 06:16:25

标签: database normalization relational

假设以下"预订"表有两列Reservation_Number和Guest_Name。 Reservation_Number是唯一的候选键:

Reservation_Number  Guest_Name  
------------------  ------------
1                   john smith  
2                   john smith  
3                   john smith  
4                   jane doe  
5                   bob anderson  

我的问题是这张桌子是否处于第3范式?

  1. 它似乎没有违反第一范式。当一个表具有主键并且每个属性的域仅包含原子值时,该表在1NF中,并且每个属性的值仅包含该域中的单个值。在此示例中,Reservation_Number是主键,Reservation_Number和Guest_Name都符合原子标准。
  2. 它似乎没有违反第二范式。当表在1NF时,表在2NF中,并且表的每个非素数属性都取决于每个候选键的整体。 Guest_Name是唯一的非素数属性,它完全依赖于唯一的候选键,即Reservation_Number。
  3. 它似乎没有违反第3范式。当表在2NF时,表在3NF中,并且表的每个非素数属性都不可传递地依赖于表的每个超级键。唯一的非素数属性Guest_Name不可传递地依赖于唯一的超级密钥,即Reservation_Number。
  4. 然而,此表中存在冗余。我明白我可以通过以下方式删除这些裁员:
    a)使用Guest_Id和Guest_Name列创建Guest表 b)用Reservation_Id FK替换Reservations表中的Guest_Name。

    但我的问题是原始预订表如何处于第3范式并且在Guest_Name列中有冗余?如果它违反了正常形式,那么如何以及为何?请帮忙!

1 个答案:

答案 0 :(得分:1)

您的示例不会违反第二和第三范式,但是如果您添加一列Guest_Telephone会怎么样。然后会违反第3范式,因为您在Guest_NameGuest_Telephone之间存在功能依赖关系。

你可以记住:

如果关系是第二范式并且密钥中只有一个附加属性,那么它将自动处于第3范式。

在您的示例中,您只需将属性Guest_Name的名称修改为Reservation_Description,并且冗余的指示将不再那么明显。

还尝试将Guest_Name拆分为两个属性Guest_FirstnameGuest_Lastname,会发生什么?

单独表示冗余并不意味着您在前三种正常表格中使用了其中一种,但正如您所说的那样,最好将预订和客人拆开。

最后一件事要提及

您的属性Guest_Name可以被视为密钥,不要求密钥必须是数字。考虑你的酒店(或任何你的预订表)容纳"数字"而不是人(好吧,我希望你有一个强大的想象力......)。有这样的架构是否有意义:

Reservation_PK Guest_FK
1              1
2              2
3              1

Guest_PK Guest_Name
1        34
2        57

当然不是,你会将Guest_Name留在原处:

Reservation_PK Guest_Name
1              34
2              57
3              34

因此,如果您不想保存除客人姓名之外的任何其他属性,我会保留您的预订表(它甚至完全符合普通表格3的所有要求)。