Например у меня есть сущность "Писатели (фио, дата рождения, дата смерти)". Писатели делятся на отечественных и иностранных. Соответственно набор атрибутов для отечественных и иностранных будет разным. Таким образом я создаю еще 2 таблицы "Отечественные (id писателя, и т.д уникальные для данного типа атрибуты)" и также "Иностранные" (id писателя, и т.д уникальные для данного типа атрибуты, например язык). Если появится третья категория писателей, то создам еще таблицу, в которой опишу уникальные для данного типа атрибуты.
Если нужно показать список категорий писателей - тогда я создам еще таблицу "Категории писателей" (id, название категории), а в таблицах "иностранные", "отечественные" и так далее, добавлю поле "writer_category_id" - которая будет ссылаться на название категории . Теперь есть список категорий, который я уже смогу показать.
Главный вопрос - Когда пользователь начнет фильтровать писателей по категориям - то в коде я должен писать через switch , что если, например id категории равен 2, то я использую таблицу иностранные, елси другой код, то другая таблица. Верно ли это - не слишком ли много будет кода? Можно ли по другому это обрабатывать? Ведь категорий может быть, например, 15 и тогда придется 15 веток для switch писать? (Даже если фабрика, то все равно придется использовать switch)
Самый радикальный, и, на мой взгляд неправильный, добавить атрибут table_name в таблицу "Категории писателей".
Для правильного вопроса надо знать половину ответа
Вообще, для такой задачи есть устоявшаяся схема:
categories (id, name) - категории (отечественный, зарубежный и т.д.)
items (id, category_id, базовый набор атрибутов) - в вашем случае авторы
attributes (id, name, type, ...) - возможные атрибуты
categories_attributes (category_id, attribute_id) - атрибуты, допустимые для категории
items_attributes (item_id, attribute_id, value) - собственно значения атрибутов
Такая схема легко расширяется, может содержать дополнительную информацию - признак обязательности атрибута в описании, список допустимых значений атрибута для типов "один из списка", "несколько из списка", единицы измерения и т.д.
Фактически Вы описали eav) Это должно решить проблему. Спасибо, что-то из головы вылетело) Хотя сразу возникает вопрос - а если появляется другая сущность, где также различные разбиения - тоже надо воссоздавать всю структура eav?
Вообще хорошую бы книгу найти по проектированию баз данных с примерами сложными)
Спасибо за ответ!
ssrdop: В предельном случае можно хранить все сущности в одной таблице, просто привязывая их к разным категориям. Но решать надо в каждом случае отдельно, EAV обычно выбирается при разреженной таблице с многочисленными атрибутами. Если заполненность таблицы хорошая, то оптимальней классическая реляционная таблица, где каждый атрибут хранится в отдельной колонке.
Опять же, можно смешивать модели, храня общие, хорошо заполненные атрибуты в основной таблице, а дополнительные или слабо заполненные - в EAV.
Самый радикальный пересмотреть список атрибутов писателей.
Вы уверены что эти "уникальные" атрибуты в таком количестве и такой важности, что требуют все отдельных таблиц?
Если отличия в категориях в 2-3 атрибута, то можно расширить число полей в таблице Писатели.
Если сильно больше, то завести одну таблицу "Атрибуты писателей" куда и сохранять "ид писателя", "имя атрибута", "значение атрибута"
Язык не имеет значения) В вашем ответе, в запросе есть "table_name" - но как раз этот table_name должен подставляться в зависимости от категории, то есть если $_GET['category_id'] = 1 , то table_name = native, если 2, то table_name = foreign и так далее. Поэтому в голову приходит только switch.
Вообще хотелось бы доставать всю информацию о писателе одним JOIN'ом)
Как раз про нормальные формы и слышал. А про мое предложение - это из книги профессора правило - если у нас сущности разбивается на категории, то выделяем общие атрибуты, а для каждой категории создаем новую таблицу, в которой будут уникальные для каждой категории сущности атрибуты. Например, у нас есть сущность доставка. Можно выделить - самовывоз (адрес магазина) и доставка по адресу ( страна, город, ....) - как раз случай из правила выше. Значит будет три таблицы. Увы это из книги профессора и не поощряется выходить за рамки правил, так как будет за это "дрю-чить"))