Зачем использовать несколько столбцов в качестве первичных ключей (составной первичный ключ)

Этот пример берется из w3schools.

CREATE TABLE Persons
(
    P_Id int NOT NULL,
    LastName varchar(255) NOT NULL,
    FirstName varchar(255),
    Address varchar(255),
    City varchar(255),
    CONSTRAINT pk_PersonID PRIMARY KEY (P_Id,LastName)
)

Я понимаю, что оба столбца вместе (P_Id и LastName) представляют собой первичный ключ для таблицы Persons. Правильно ли это?

  • Почему кто-то хочет использовать несколько столбцов в качестве первичных ключей вместо одного столбца?
  • Сколько столбцов можно использовать вместе в качестве первичного ключа в данной таблице?

Ответ 1

Ваше понимание верное.

Вы бы сделали это во многих случаях. Один пример - в отношениях типа OrderHeader и OrderDetail. PK в OrderHeader может быть OrderNumber. PK в OrderDetail может быть OrderNumber AND LineNumber. Если бы это было одно из двух, это не было бы уникальным, но сочетание двух гарантировано уникальным.

Альтернативой является использование сгенерированного (неинтеллектуального) первичного ключа, например, в этом случае OrderDetailId. Но тогда вы не всегда будете видеть отношения так же легко. Некоторые люди предпочитают один путь; некоторые предпочитают другой путь.

Ответ 2

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

Create Table Person(
PersonID int Not Null,
FirstName varchar(50),
LastName varchar(50),
Constraint PK_Person PRIMARY KEY (PersonID))

Create Table Group (
GroupId int Not Null,
GroupName varchar(50),
Constraint PK_Group PRIMARY KEY (GroupId))

Create Table GroupMember (
GroupId int Not Null,
PersonId int Not Null,
CONSTRAINT FK_GroupMember_Group FOREIGN KEY (GroupId) References Group(GroupId),
CONSTRAINT FK_GroupMember_Person FOREIGN KEY (PersonId) References Person(PersonId),
CONSTRAINT PK_GroupMember PRIMARY KEY (GroupId, PersonID))

Ответ 3

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

Их выбор, возможно, вводит вас в заблуждение, объединяя бессмысленный ключ (P_Id) и естественный ключ (LastName). Этот нечетный выбор первичного ключа говорит, что следующие строки действительны в соответствии с схемой и необходимы для однозначной идентификации ученика. Интуитивно это не имеет смысла.

1234     Jobs
1234     Gates

Дальнейшее чтение: Отличная дискуссия с основным ключом или просто Google meaningless primary keys или даже прочесть это Вопрос SO

FWIW. Мои 2 цента должны избегать многоколоночных первичных ключей и использовать одно сгенерированное поле идентификатора (суррогатная клавиша) в качестве первичного ключа и при необходимости добавлять дополнительные (уникальные) ограничения.

Ответ 4

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

Ответ 5

Вопрос второй части

Сколько столбцов может использоваться вместе как первичный ключ в данной таблице?

специфична для реализации: она определена в используемой СУБД. [1], [2], [3] Вам необходимо проверить техническую спецификацию используемой системы баз данных. Некоторые из них очень детализированы, некоторые - нет. Поиск в Интернете о таком ограничении может быть затруднен, потому что терминология меняется. Термин составной первичный ключ должен быть обязательным;)

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


Ответ 6

Да, оба они образуют первичный ключ. Особенно в таблицах, где нет суррогатного ключа, может потребоваться указать несколько атрибутов как уникальный идентификатор для каждой записи (плохой пример: таблица с именем и фамилией может потребовать, чтобы их комбинация была уникальной).

Ответ 7

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

Ответ 8

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

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

Вторая таблица была "characters" — их имена и краткое описание. Первичный ключ находился в "charname".

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