Если таблица базы данных, содержащая два столбца, которые являются внешними ключами, имеет третий столбец, который является первичным ключом?

Я предполагаю, что нет, поскольку внешние ключи являются первичными ключами в своих собственных таблицах, поэтому они будут уникальными.

Дополнительная информация

Я использую 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?
========================

Эпилог

Спасибо за отличные ответы. Я узнал о составных ключах и, рассмотрев мой конкретный случай, решил сделать столбец image_id в таблице galleries_images первичным ключом. Таким образом, изображения могут быть связаны только с одной галереей, и это то, что я хочу.

Я также собираюсь реализовать столбец order_num в galleries_images, который я буду использовать логику PHP для поддержки. Таким образом, пользователь может размещать изображения в определенном порядке в каждой галерее. Я закончил с этим:

============================
| galleries_images         |
|--------------------------|
| PK, FK | image_id        |
| FK     | gallery_id      | 
|        | order_num       |
============================

Еще раз спасибо!

Эпилог II

Спасибо тем, кто указал, что мне даже не нужна эта таблица. На самом деле я не предоставил самую полную информацию. В итоге я полностью потерял таблицу galleries_images и просто добавил gallery_id в качестве внешнего ключа в таблицу images. В любом случае, я все еще узнал больше, чем я думал, и буду благодарен за помощь.

Ответ 1

Все таблицы должны иметь первичный ключ.

Нет необходимости создавать новый суррогатный столбец, чтобы действовать как первичный ключ. Взяв пример Джона, было бы вполне приемлемо иметь составной первичный ключ с 2 полями первичного ключа из других таблиц и поле даты.

С прагматической точки зрения, хотя иногда создание нового суррогатного столбца может быть проще работать, чем сложный, хотя, если PK сам упоминается в еще одной таблице или для привязки к различным элементам управления, которые не обрабатывают составные первичные ключевой колодец.

Edit

После обновления к вашему вопросу я просто сделаю основной составной элемент на gallery_id, image_id. Я не вижу никакой пользы от добавления нового столбца.

Ответ 2

Теоретически, если комбинация двух внешних ключей (FKs) уникальна в таблице или если комбинация двух FK и некоторого другого столбца уникальна, тогда таблица имеет составной первичный ключ, и нет строгая необходимость ввести другой ключ в качестве суррогатного первичного ключа. Однако нет ничего необычного в том, что люди добавляют дополнительный ключ. Отчасти это зависит от того, что будет использоваться для данных в таблице с составным первичным ключом. Если он описывает то, что будет иметь строки из других связанных с ним таблиц, тогда может возникнуть смысл ввести простой PK.

Некоторое программное обеспечение, по-видимому, требует простых PK, даже если модель реляционных данных не работает.

Ответ 3

Ответ обычно "да". Тип таблицы, которую вы описываете, представляет собой таблицу ассоциаций, в которой хранятся ассоциации. Поскольку эти записи интересны сами по себе, и потому, что вы, вероятно, захотите посмотреть их позже, они должны иметь значимую идентичность.

Например, возможно, у вас есть таблица players и таблица matchups для вашей теннисной лиги. matchups может содержать не что иное, как внешние ключи двух игроков, играющих друг против друга; это связь между двумя игроками.

Но позже вы можете захотеть записать другую информацию, относящуюся к этой ассоциации: время матча, счет игры и т.д. И, конечно же, как только вы захотите иметь более одного матча между двумя игроками, вам нужно будет различать каждый матч. Таким образом, вы захотите дать каждому matchup свою собственную идентификацию в виде первичного ключа.


Update:

========================
| galleries_images     |
|----------------------|
| FK | gallery_id      |
| FK | image_id        |  <----- Should I add a PK to this table?
========================

В вашем конкретном примере, вероятно, полезно иметь первичный ключ здесь. Как только вам нужно записать какие-либо метаданные об ассоциации, вы захотите получить этот первичный ключ. Кроме того, если одно и то же изображение можно добавить в одну и ту же галерею более одного раза, для разграничения между двумя записями потребуется первичный ключ.

Ответ 4

Если одно конкретное изображение может быть связано только с одной отдельной галереей, то комбинации в вашей таблице галерей-изображений уникальны, и вы можете использовать эту пару полей в качестве ПК.
Если комбинации галерей и изображений можно дублировать ИЛИ если ваша схема содержит больше таблиц, которые бывают детьми из этих галерей-изображений,
THEN Я бы предложил, чтобы вы включили дополнительное поле, которое будет PK.

Ответ 5

Этот ответ связан с его вопросом о блокировке: я знаю, должна быть новая тема, но что угодно. Пожалуйста, не уменьшайте это просто.

Например, вы можете создать таблицу Order_image_lock (идентификатор галереи (первичный ключ), start_time).

Создайте 3 метода /sprocs: GetLock, CheckLock, DropLock.

Если вы хотите изменить порядок портфеля, вы вызываете GetLock, который вставляет (gallary_id, sysdate).

Если это сработает, вы можете продолжить. Если он не работает на ПК, кто-то другой переупорядочивает, поднимает исключение.

Когда вы будете готовы к переупорядочиванию, вызовите CheckLock, чтобы узнать, находится ли ваша блокировка по-прежнему (вы поймете, почему), если у вас есть это, обновите измененные значения, если не перейдите в GetLock.

Когда вы закончите, DropLock удалит запись.

Серверный процесс может зачистить таблицу для блокировок более чем за 6 минут. Для разъединений или людей, которые покидают экран и отправляются на обед.

Добавьте столбец user_id в эту таблицу, чтобы вы могли сообщить, кто имеет то, что может заблокировать другой пользователь.

Это будет значительно лучше, чем блокировка строк. у некоторых dbms есть конечное количество блокировок, что заставляет их выполнять "блокировку эскалации", когда несколько блокировок строк преобразуются в блокировку страницы, пока не будет слишком много блокировок страниц и будут преобразованы в блокировку таблицы... вам нужно проверить, как ваши RDBM работают с большими объемами блокировки... если вы планируете масштабировать.

Ответ 6

Вы говорите, что внешние ключи являются первичными ключами в своих собственных таблицах. Это означает, что они уникальны в этих таблицах. Однако это не значит, что они уникальны в этой таблице.

Я обычно обнаружил, что лучше всего создать первичный ключ в таблице базы данных. Рано или поздно вы обнаружите, что вам это нужно, поэтому почему бы не включить новый первичный ключ с самого начала?