包含两个外键列的数据库表是否应该有第三列作为主键?

Mik*_*ore 11 database database-design primary-key

我猜不是,因为外键是他们自己的表中的主键,所以它们将是唯一的.

更多信息

我正在使用MySQL,以下三个表正在使用InnoDB引擎.

=======================    =======================
| galleries           |    | images              |
|---------------------|    |---------------------|
| PK | gallery_id     |    | PK | image_id       |
|    | name           |    |    | title          |
|    | description    |    |    | description    |
|    | max_images     |    |    | filename       |
|    | enabled        |    |    | enabled        |
=======================    =======================

========================
| galleries_images     |
|----------------------|
| FK | gallery_id      |
| FK | image_id        |  <----- Should I add a PK to this table?
========================
Run Code Online (Sandbox Code Playgroud)

结语

谢谢你的出色答案.我了解了复合键,在考虑了我的具体情况之后,我决定image_idgalleries_images表中的列作为主键.这样,图像可能只与一个图库相关联,这就是我想要的.

我还将实现一个order_numgalleries_images,我将使用PHP逻辑进行维护.这样,用户可以按照特定顺序在每个图库中放置图像.我最终得到了这个:

============================
| galleries_images         |
|--------------------------|
| PK, FK | image_id        |
| FK     | gallery_id      | 
|        | order_num       |
============================
Run Code Online (Sandbox Code Playgroud)

再次感谢!

结语II

感谢那些指出我甚至不需要这张桌子的人.我没有提供最完整的信息.我最终galleries_images完全放弃了桌子,只是将其gallery_id作为外键添加到images表格中.无论如何,我仍然学到了比我想象的更多的东西,并感谢你的帮助.

Jon*_*ler 10

理论上,如果两个外键(FK)的组合在表中是唯一的,或者如果两个FK的组合加上一些其他列是唯一的,则表具有复合主键,并且没有严格的需要引入另一个密钥作为代理主键.但是,发现人们确实添加了额外的密钥并不罕见.在某种程度上,它取决于具有复合主键的表中的数据将用于什么.如果它描述的东西本身会有与其相关的其他表中的行,那么引入一个简单的PK可能是有意义的.

有些软件似乎需要简单的PK,即使关系数据模型没有.


Mar*_*ith 6

所有表都应该有一个主键.

但是,没有必要创建新的代理列来充当主键.以约翰的例子为例,拥有一个复合主键,其中包含来自其他表和日期字段的2个主键字段是完全可以接受的.

从实用的角度来看虽然有时创建一个新的代理列可能比复合列更容易使用,但如果PK本身在另一个表中引用或者绑定到不能处理复合主键的各种控件.

编辑

在更新您的问题之后,我将在gallery_id,image_id上​​创建主键复合.我没有看到添加新列的任何好处.

  • 虽然我手头没有证据,但我认为使用整数代理键比使用复合键更快加入目的.出于这个原因,我总是在所有表上创建int代理键. (2认同)

Joh*_*lla 5

答案通常是"是".您描述的表是一种关联表,用于存储关联.因为这些记录本身很有趣,并且因为您可能希望以后查找它们,所以它们应该具有有意义的身份.

例如,也许你有一张players桌子和一张matchups桌子用于你的网球联赛.matchups可能只包含彼此对战的两名球员的外键; 这是两个球员之间的关联.

但是稍后您可能想要记录特定于该关联的其他信息:比赛发生的时间,比赛的得分等等.而且,当然,只要你想在同一个两个球员之间进行多场比赛,你就需要区分每场比赛.因此,您需要以matchup主键的形式为每个人提供自己的身份.


更新:

========================
| galleries_images     |
|----------------------|
| FK | gallery_id      |
| FK | image_id        |  <----- Should I add a PK to this table?
========================
Run Code Online (Sandbox Code Playgroud)

在您的具体示例中,在此处拥有主键可能很有用.只要您需要记录关于关联的任何元数据,您就会想要拥有该主键.此外,如果可以将同一图像多次添加到同一图库中,则需要主键来区分这两个记录.