sql Внешние ключи: преимущества, недостатки, альтернативы

Forums:

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

Пример использования внешнего ключа

Представим, что у нас есть две таблицы: Students (Студенты) и Courses (Курсы). Каждый студент может быть зарегистрирован на несколько курсов, и каждый курс может иметь несколько студентов. Мы можем использовать внешний ключ, чтобы установить связь между этими таблицами.

CREATE TABLE Students (
        StudentID int PRIMARY KEY,
        StudentName varchar(255)
    );

CREATE TABLE Courses (
        CourseID int PRIMARY KEY,
        CourseName varchar(255),
        StudentID int,
        FOREIGN KEY (StudentID) REFERENCES Students(StudentID)
    );

В данном примере, столбец StudentID в таблице Courses является внешним ключом, который ссылается на столбец StudentID в таблице Students. Это позволяет связать студента из таблицы Students с соответствующим курсом в таблице Courses.
Определение внешнего ключа в MySQL выглядит следующим образом:

ALTER TABLE имя_таблицы
ADD CONSTRAINT имя_констрейнта
FOREIGN KEY (столбец_таблицы) REFERENCES имя_таблицы_ссылки (столбец_таблицы_ссылки);

Действия при обновлении и удалении данных

При определении внешнего ключа можно задать правила для каскадных обновлений и удалений с помощью следующих опций: ON DELETE ON UPDATE.
Рассмотрим доступные режимы:

  • CASCADE - Автоматически удаляет или обновляет связанные строки в дочерней таблице при изменении данных в родительской.
  • RESTRICT - Запрещает удаление или обновление строки в родительской таблице, пока есть ссылки на нее.
  • SET NULL - Устанавливает значение NULL в столбцах внешнего ключа в дочерней таблице при удалении связанных данных в родительской.
  • SET DEFAULT - При удалении связанной строки из главной таблицы устанавливает для столбца внешнего ключа значение по умолчанию, которое задается с помощью атрибуты DEFAULT. Если для столбца не задано значение по умолчанию, то в качестве него применяется значение NULL.

По умолчанию используется режим NO ACTION, который аналогичен RESTRICT. Какой режим выбрать, зависит от бизнес-логики приложения. CASCADE удобен, когда нужно каскадно обновлять данные. А RESTRICT позволяет избежать случайного удаления.

Преимущества использования внешнего ключа в MySQL

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

Ограничения и недостатки внешнего ключа MySQL

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

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

  5. Сложность при вставке и обновлении данных
  6. Использование внешних ключей в MySQL может также усложнить процесс вставки и обновления данных. При вставке или обновлении значений в таблицу с включенными внешними ключами необходимо убедиться, что значения, на которые ссылаются внешние ключи, существуют в связанных таблицах. В противном случае операции вставки и обновления могут быть отклонены.

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

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

Альтернативы внешним ключам в SQL

Помимо внешних ключей, в SQL существуют и другие способы обеспечить целостность данных в связанных таблицах:

  • Триггеры - Позволяют выполнить дополнительную логику при добавлении, изменении или удалении данных. Например, с помощью триггеров можно реализовать каскадное удаление, проверку referential integrity.
  • Хранимые процедуры - Все операции с данными можно инкапсулировать в хранимых процедурах. Это позволит централизованно управлять правилами целостности данных.
  • Каскадное обновление на уровне приложения - Логику внешних ключей можно реализовать в коде приложения, выполняя запросы к базе данных.

Достоинства альтернативных подходов:

  • Больше гибкости в реализации бизнес-логики
  • Легче отладка и тестирование
  • Возможность реализовать сложные сценарии обновления данных

Недостатки:

  • Увеличение сложности кода приложения
  • Потенциально снижение производительности
  • Бóльшие усилия по поддержке и сопровождению

Источники:
Внешний ключ SQL (Foreign Key) для объединения двух таблиц
Внешние ключи
Что такое внешний ключ в SQL: определение, использование и преимущества
Внешний ключ MySQL: что это и как использовать

Key Words for FKN + antitotal forum (CS VSU):