我将以下单个表分解为3个表,以便基于以下依赖关系和组合键(FirstName,LastName,Career)将其转换为3NF:
第一个范式:
FirstName, LastName, Address, Career, Pay, Managerial
依赖项:
FirstName, LastName -> Address
Career -> Pay, Managerial
第三种正常形式:
People (FirstName, LastName, Career)
Addresses (FirstName, LastName, Address)
Careers (Career, Pay, Managerial)
在本示例中,我们可以假设(FirstName,LastName)和(Career)是唯一的,以避免在Addresses和Careers表中为其创建ID。
我是否认为此模式中没有外键? “地址”和“职业”中的键仅部分组成“人员”中的键。还是人们实际上有2个外键:FK(名字,姓氏)和FK(职业)以及1个主键:PK(名字,姓氏,职业)?
答案 0 :(得分:2)
通过分解归一化为较高NF的表将替换为其他表,这些表自然会重新加入该表,这是该表的投影。因此,对于任何共享列,两个组件都具有相同的子行值集,因为它们都是原始对象的投影。因此,当/如果后一个列集在后一个表中形成CK(候选键)时,则从列集和表到另一个列集和表之间有一个FK(外键)。
在这里,如果原始FD构成封面:您有人员CK {{FirstName,LastName,Career}},地址CK {{FirstName,LastName}}和Careers CK {{Career}}。因此,FK是人员FK,{FirstName,LastName}是地址,而{Career}是职业。
PS通常,在进行归一化时,我们意识到我们不希望原始表的投影,而是希望表的标题类似于某些组件,但包含更多行。 (有时,这被归一化为归一化的一部分。)(尽管归一化仅针对更新异常,我们检测并重新设计删除和插入异常。)然后,我们选择的这些不同表通常不具有与CK相同的CK或子行值集归一化组件。
PS对较高NF的归一化不会引入新列。其中包括id列。
PS相对而言,“ FK”通常涉及一个列集。但这可能意味着引用了另一个的列列表。或一个列列表,其中每个名称在引用另一个名称时都会出现。但是SQL“ FK”并不表示FK的那些关系概念中的任何一种,它或多或少表示外键。同样,SQL“ PK”或多或少表示主超级键。 See this answer.
答案 1 :(得分:1)
您不正确。我不同意您的架构,但是Person.Career
是对Careers.Career
的外键引用。
类似地,模式中的某处可能应该有一个地址ID和一个人ID。
答案 2 :(得分:-2)
实际上,您有多对多的关系。因此,一个地址可以被许多人取用。一个人可以有多个地址。 在这种情况下,人员表中将有重复项,地址表中将有重复项。外键将有所不同,但其他部分将重复。 有表是很常见的:
人员地址(person_id,address_id,occulied_from,占领的耕种)
PersonCareers(person_id,事业ID,employee_from,employee_till)
另一部分是关系数据库理论中描述的,没有RDBMS提供您所提到的复杂密钥