mysql - 作为多个复合 FK 约束一部分的一列是否有效且良好的设计决策?

标签 mysql database database-design foreign-keys relational-database

表中的一列可以作为两个复合 FK 约束的一部分吗?

假设我们有多个业务分支机构,并且有两个不同的实体,每个实体都属于一个特定的分支机构。

现在我们想要关联这两个实体(多对多),但仅当它们属于同一分支时才允许关联。

所以我们会有三个表:

  • 实体A
  • 实体B
  • 实体

在我看来,我有几个选择:

1) 对所有 PK 使用代理 key

  • EntityA(entitya_id(pk)、branch_id(fk)、其他列)
  • EntityB(entityb_id(pk)、branch_id(fk)、其他列)
  • 实体(entities_id (pk)、entitya_id (fk)、entityb_id (fk))

这个的问题是我需要触发器内的 SELECT 语句来进行验证。我宁愿不这样做。此外,SELECT 语句变得更加复杂,因为它通常需要 JOIN 来访问某些信息。

2)使用自然复合键

  • EntityA(PK:entitya_idbranch_id)
  • EntityB(PK:entityb_idbranch_id)
  • 实体(PK entitya_identitya_branch_identityb_identityb_branch_id)

这也需要在触发器中进行验证,但至少我只需要对 NEW 值进行简单的 IF 比较。另一方面,键/列的数量快速增长,即使在简单的情况下,表也可能具有巨大的复合键和大量冗余数据。

3) 也使用自然复合键,但只有一列引用两个表

这是我的第一选择,但我认为不允许在多个表中有一个列引用键。虽然您不能仅使用一列来完成此操作,但显然允许该列成为多个复合约束的一部分,如 here 所示。

  • EntityA(PK:entitya_idbranch_id)
  • EntityB(PK:entityb_idbranch_id)
  • 实体(PK:entitya_identityb_idbranch_id)

FK 定义如下:

CONSTRAINT `entities_entitya`
    FOREIGN KEY (`entitya_id`, `branch_id`)
    REFERENCES `entitya` (`entitya_id`, `branch_id`)
    ON DELETE CASCADE
    ON UPDATE RESTRICT,
CONSTRAINT `entities_entityb`
    FOREIGN KEY (`entityb_id`, `branch_id`)
    REFERENCES `entityb` (`entityb_id`, `branch_id`)
    ON DELETE CASCADE
    ON UPDATE RESTRICT

因此branch_id成为某种共享FK

重复我的问题:

  • 这样做合法吗?
  • 它是否违反了某些规范?
  • 这会不会在我脸上爆炸?

最佳答案

您的解决方案 #3 没有任何问题,我认为这是满足您的验证要求的一个聪明的解决方案。它准确地模拟了现实世界的要求 - 两个实体必须属于同一个分支。

我不知道它会如何导致任何问题,除非假设需求稍后会发生变化。例如,您可能会得到一个稍微不同的要求,即两个分支可以不同,只要它们以某种方式相互关联即可。

在这种情况下,您需要两个不同的列,但是您还需要在两个不同的外键约束中使用每个分支列:

CREATE TABLE Entities (
  entitya_id        INT,
  entitya_branch_id INT,
  entityb_id        INT,
  entityb_branch_id INT,
  FOREIGN KEY (entitya_id, entitya_branch_id) 
    REFERENCES entitya(entitya_id, branch_id),
  FOREIGN KEY (entityb_id, entityb_branch_id) 
    REFERENCES entitya(entityb_id, branch_id),
  FOREIGN KEY (entitya_branch_id, entityb_branch_id) 
    REFERENCES EntityAffiliations(entitya_branch_id, entityb_branch_id)
)

关于mysql - 作为多个复合 FK 约束一部分的一列是否有效且良好的设计决策?,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/54496852/

相关文章:

mysql - 存储过程中的 DML 是否在单个事务中运行?

mysql - “多对二”关系

php - 如何链接单个表中的多行 - MySql

mysql - 如何使用mysql上最有效的方法生成最后一个表?

mysql - 如何计算行中的datediff

php - mysql_query 没有正确插入行

mysql - 数据库:表设计/结构

mysql - Logstash:Elasticsearch 的未知设置 ‘“index”

mysql - 如何使用 odbc for filemaker 将数据从 filemaker pro 移动到 microsoft sql server studio

database - 提高 JOIN 和子 SELECT 的查询性能