Соединение таблиц на основе внешних ключей - PullRequest
3 голосов
/ 02 марта 2011

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

Как большинство людей делают это?

101 способ сделать это - запросить в этой таблице данные, включая внешние ключи, а затем запросить соответствующие таблицы, чтобы получить значение каждого ключа. Это может быть много запросов (~ 10).

Вопрос 1: Я думаю, что мог бы написать 1 запрос с кучей объединений. Это было бы лучше?

Этот подход также требует, чтобы скрипт запроса знал, какие поля таблицы являются внешними ключами. Поскольку у меня есть много подобных таблиц, но все с разными полями, это означает, что писать хорошие универсальные функции сложно. Таблицы MySQL InnoDB допускают внешние ограничения. Я знаю, что база данных настроена правильно.

Вопрос 2: Как насчет идеи запроса таблицы и определения ограничений, а затем сопоставления их с использованием любого процесса, о котором я решу из Вопроса 1. Мне нравится эта идея, но я никогда не вижу ее используется в коде. Заставляет меня думать, что это не очень хорошая идея по какой-то причине. Я бы использовал что-то вроде SHOW CREATE TABLE tbl_name; чтобы найти, какие ограничения / отношения существуют для этой таблицы.

Спасибо за любые предложения или советы.

Ответы [ 3 ]

1 голос
/ 02 марта 2011

На каком-то уровне система должна выполнять запросы с использованием объединений, независимо от того, написаны ли эти запросы явным образом программистом приложения или автоматически сгенерированы уровнем доступа к данным . Вариант 1 определенно лучше, чем наивный вариант. Что касается некоторых других вариантов создания запросов (отнюдь не исчерпывающий список):

  • Вы можете абстрагироваться от всех операций с базой данных, подобно тому, как PDO абстрагирует от операций соединения и запросов (то есть, подготавливает и выполняет запросы). Используйте это для получения метаданных таблицы, включая внешние ключи, которые затем можно использовать для автоматического создания запросов.
  • Вы можете написать спецификации объекта в каком-либо другом формате (например, XML) и класс, который будет использовать его для генерации классов PHP и таблиц базы данных. Вы найдете это больше в корпоративных приложениях, чем в небольших проектах. Эта опция имеет больше накладных расходов, чем другие, и поэтому не подходит, если у вас есть только несколько классов для моделирования. Появление этой опции также может быть следствием Закона Конвея , который я впервые услышал как вариант Ричарда Фэрли: «Структура системы отражает структуру организации, которая ее построила».
  • Вы можете использовать LINQ -подобный подход. В PHP это будет означать написание многочисленных функций или методов, которые программист приложения может связать вместе, что приведет к созданию запроса. Программисты приложений несут полную ответственность за объединение таблиц, хотя сами никогда не пишут JOIN.

Вместо того, чтобы думать о том, как создавать запросы, лучший проблемный подход состоит в том, чтобы подумать о том, как взаимодействовать с БД и приложением. Это приводит к шаблонам , таким как Data Mapper и Active Record , которые попадают в категорию Object-Relational mapping ( ORM ). Обратите внимание, что некоторые шаблоны (такие как AR), другие методы ORM и даже сама ORM имеют свои собственные проблемы. Любой из описанных выше вариантов создания запроса может использоваться при реализации шаблона доступа к данным.

Проблема с использованием SHOW CREATE TABLE заключается в том, что он не работает с большинством (всеми?) Другими СУБД. Если вы хотите объединить свое приложение с MySQL, продолжайте, но решение может преследовать вас.

1 голос
/ 02 марта 2011

Вы говорите о написании «хороших общих функций», но я думаю, что вы думаете, что СЛИШКОМ универсальный здесь.

Лично я бы просто написал запрос с кучей соединений.Если вы хотите абстрагировать всю эту объединяющую логику и не беспокоиться об этом, то вам, вероятно, стоит подумать об использовании ORM вместо прямой записи SQL.

0 голосов
/ 02 марта 2011

С каким количеством записей вы работаете, как в основных таблицах данных, так и в таблицах поиска?

Как правило, вы должны присоединить таблицы поиска к основной таблице. Если у вас чрезмерное количество объединений, и здесь не так много UDF, вполне вероятно, что таблицу следует нормализовать немного больше. Если нормализация в порядке и основная таблица данных действительно широка, вы все равно можете разделить таблицу на несколько таблиц со связями 1: 1, чтобы отделить часто используемые столбцы от редко используемых столбцов.

MySQL включает поддержку каталога ANSI INFORMATION_SCHEMA.REFERENTIAL_CONSTRAINTS. Вы можете использовать это, чтобы собрать информацию о существующих отношениях FK.

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

...