
在这个数据库中,key1 & key2构成了table4的复合主键,但是我能够向table3添加一个外键,其中只包含key1。
为什么MySQL允许这样做?上面的数据库设计完全没有意义吗?
发布于 2017-07-01 03:44:02
这个答案将问题的“向table3添加外键”表示在table3中添加了一个FK (外键),引用了table4的复合PK (主键)的一个列。在标准SQL中,FK可以引用PK的适当/较小的子集。
另一个答案可能会使用“向table3添加外键”来表示在table4中添加了一个FK,它包含PK引用table3的一列。表中的FK列集独立于表中的任何PK或唯一声明。
在标准SQL中,FK可以引用PK的适当/较小的子集。
引用的列列表必须声明为主键或唯一。(主键创建唯一的NULL约束。)(约束必须是显式的,即使包含唯一集合的所有非空列都必须是唯一的。)
不幸的是,MySQL允许您声明引用非唯一列列表的FK。即使这样的FK或引用非空列(在标准SQL中为OK)的引用没有得到正确的实现,而且文档本身建议不要这样做:
对非唯一键或包含空值的键的外键引用的处理对于诸如UPDATE或DELETE级联之类的操作没有很好的定义。建议您使用只引用唯一(或主)和非空的键的外键。
(您可以考虑什么是定义良好的操作,哪些不是定义良好的操作,因为文档实际上并没有明确说明。)
关系型与SQL型
在关系模型中,FK引用CK (候选键)。超级键是唯一的列集。CK是一个超级键,不包含较小的超键。一个CK可以称为PK (主键)。当列集的值必须出现在其他地方时,我们说有一个IND (包含依赖项)。FK是对CK的IND。当IND到超级键时,我们可以称之为“外键”。
SQL PK或UNIQUE NOT NULL声明超级键。如果它不包含声明为SQL PK或UNIQUE NOT NULL的较小列集,则为CK。SQL FK声明了一个外部超级键。因此,SQL实际上可能是关系PK (因此是CK),唯一的NULL实际上可能是CK。其中之一的SQL实际上是一个关系FK。
发布于 2017-06-30 06:33:15
外键根本不依赖主键。事实上,它们与主键无关。
主键的唯一用途是唯一地标识一行。
外键的目的是确保引用表(子表)中的每个条目必须在引用表(父表)中有一个条目。在MySQL中,在引用的列上必须有一个索引(不一定是主键或唯一键,一个简单的索引就足够了),这只是一个技术要求。
所以你的设计是有意义的。
https://stackoverflow.com/questions/44838200
复制相似问题