Согласно Пяти Простым Ошибкам Проектирования баз данных Необходимо Избежать Сенатором Anith, использование общей справочной таблицы для хранения возможных состояний для объекта является частой ошибкой.
Редактирование + Ответ: числа в статье Anith не хорошо маркированы - я думал, что и рисунок 1 и рисунок 2 являются примерами плохого дизайна, тогда как рисунок 2 является хорошим дизайном. Уф, волновался там на мгновение.
Я сохраню свой вопрос ниже для ссылки.
"Вы теряете средства гарантировать точные данные; ограничения. Путем объединения различных объектов в единственную таблицу у Вас нет декларативных средств ограничить значения определенной категории".
То, как ограничение оценивает, теряет точность?"Вы вынуждены представить каждый тип данных как строку с этим типом универсальной справочной таблицы".
Если я хочу представить другой тип данных, я могу добавить столбец для него к моей справочной таблице."Вы посвящаете себя жесткости и последующей сложности".
Как?В-четвертых и наконец, Вы сталкиваетесь с физическими проблемами реализации.
Я не вижу почему.
Я не соглашаюсь с большинством приведенных причин и хотел бы некоторый объективный критический анализ на своем неправильном? логика.
При приведении примера заданий в сервисе восстановления со многими возможными состояниями, которые обычно имеют естественный поток, давайте возьмем a JobStatus
таблица:
Возможно, некоторые из этих состояний могут быть нормализованы к таблицам как Couriered Items
, Completed Jobs
и Quotes
(с состояниями Pending/Accepted/Rejected), но это чувствует себя подобно ненужной сложности схемы.
Другой типичный пример был бы OrderStatus
таблица для ограничения состояния порядка:
Заголовки состояния и описания находятся в одном месте для редактирования и легки к лесам как выпадающее с внешним ключом для динамических применений данных. Это работало хорошо на меня в прошлом. Если бизнес-правила диктуют создание нового статуса заказа, я могу просто добавить его к OrderStatus
таблица, не восстанавливая мой код.
Почему это - плохая практика?
Редактирования: Я добавил причину Anith для своего вопроса и попытался остаться объективным.
--
Анит Сен не советует иметь единую таблицу поиска для всех кодов поиска . В этом значение столбца категории
в его примере. Отдельная таблица для каждой категории - отличный вариант.
Это связано с тем, что:
В ваших примерах JobStatus и OrderStatus - это разные категории. применимо к отдельным организациям. Вот почему им нужны разные справочные таблицы. Нет даже проблемы с совместным использованием одной и той же кодовой таблицы в нескольких разных таблицах данных. Проблематично, когда у нас есть отдельные таблицы данных (сущности), для которых некоторые статусы не подходят: пора разделить коды на отдельные справочные таблицы.
править
Я вижу, вы отредактировали свой пост, чтобы процитировать все точки зрения Анит. Я думаю, что самый важный момент - это первый, касающийся ограничений.Если вы хотите ограничить столбец ORDERS.STATUS значениями из категории OrderStatus, вам потребуется отдельная таблица для принудительного применения внешнего ключа. Ваши альтернативы:
Все эти варианты - отстой с точки зрения базы данных.
Я не думаю, что ваш пример статуса заказа действительно соответствует тому, что обсуждается в статье - таблица OrderStatus выглядит так, как автор думает, что вы должны это сделать.
Существует множество причин, по которым «таблица поиска для завершения всех таблиц поиска» является плохим подходом, в том числе тот факт, что вы не можете определить отношения, и объединение становится более трудным, чем должно быть.
У вас уже есть правильный ответ, поэтому это замечание является дополнительным.
Большая проблема с OTLT (одна настоящая таблица поиска) заключается в том, что вы в конечном итоге помещаете значения из разных доменов в один и тот же столбец, а затем используете отдельный столбец для устранения неоднозначности.
В ваших примерах вы использовали числа рядом с описанием каждого статуса. Если эти числа являются числовыми кодами, как я думаю, они должны быть, тогда вам не нужно значение 4, означающее «ожидание подтверждения клиента», в том же столбце, что и значение 4, означающее «Отменено». Если вы сделаете это, то вы не сможете использовать этот столбец в качестве ПК для вашей единственной истинной таблицы поиска.
Если вы дадите своей единственной истинной таблице поиска другой столбец, назовите ее «CodeType» и используйте «CodeType» и «Code» в качестве составного PK, то вы усложните больше, чем вносите, имея отдельную таблицу поиска для каждого кода. тип.
Короткий ответ таков: не помещайте значения из разных доменов в один столбец. Это всегда доставляет больше хлопот, чем спасает.
Между прочим, можно создать представление, которое объединяет все отдельные таблицы поиска в единую гигантскую таблицу поиска. Это может быть полезно в некоторых очень необычных ситуациях.
Проблема заключается в создании центральной таблицы, в которой смешано много разных кодов. Вы либо а) должны включить дополнительные столбцы, чтобы гарантировать, что заказы ссылаются только на статусы заказов в этой таблице, или б) в итоге вы получите задание, которое отправляется, а заказ - «безнадежно и готов к вывозу»
Изменить
Теперь вы добавили причины Анит и причины вашего отказа. Опять же, Анит имеет в виду наличие одной центральной таблицы для всех значений поиска в вашей базе данных. Итак, давайте посмотрим на номер 2:
«Вы вынуждены представлять каждый тип данных как строку с этим типом общей таблицы поиска».
Если я хочу {{ 1}} представляют другой тип данных, я могу добавить столбец для него в свою таблицу поиска.
Но с одной центральной таблицей для всех поисков теперь вы добавляете столбец, который должен заполняться только для одной конкретной операции поиска. Но собираетесь ли вы добавить ограничения CHECK, обеспечивающие это (фактически создавая NULL, но НЕ NULL, если ограничение Category = 'X' для столбца). Это может превратиться в кошмар обслуживания.
У вас должна быть отдельная таблица поиска для каждого запроса, который вам нужен, а не только один. Когда он у вас есть, он становится узким местом в системе, поскольку большинству запросов может потребоваться присоединение к таблице или запрос только к этой таблице. Плюс, честно говоря, это усложняет обслуживание и понимание системы, когда вы приходите в компанию новичком.
Кроме того, вы нарушили целостность данных из-за отношений PK / FK. Если у вас есть отдельные таблицы, FK означает, что вы не можете вводить значения, не входящие в справочную таблицу. Если вы используете одну большую таблицу, вы можете вводить значения, не соответствующие ситуации. Я помню одну базу данных, в которой я работал, где значение person_type было «Да» для некоторых записей.