Стоит ли создавать отдельные таблицы для разных видов продукции?


25

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

Типы продукции: модели, детали, комплекты запасных частей и опции.

Вариант A (первый дизайн): я планировал иметь отдельные таблицы для указанных выше типов продуктов. Я бы сказал, что около 75% полей будут одинаковыми в каждой таблице.

Я создал каждый тип продукта в виде отдельных таблиц из-за связей, которые мне нужно создать между ними. Например, модель может иметь много опций, а опция может иметь много моделей. Опция также может иметь много деталей, а деталь может иметь много опций ... и так далее ...

Вариант B: вместо отдельных таблиц я мог бы создать таблицу с именем Product, которая включает модели, детали, комплекты запасных частей и опции. Я мог бы иметь одно поле с именем type, чтобы различать модель, опции и т. Д. Я предполагаю, что недостатком является то, что несколько полей никогда не будут использоваться (оставлены пустыми) для определенных типов продуктов. Я предполагаю, что именно здесь "не лучшие практики" вступят в игру ..

Вариант B значительно уменьшит сложность дизайна БД. Мне также не пришлось бы беспокоиться о ссылках на кучу таблиц при извлечении данных для запросов ...


2
На этом этапе я предлагаю вам создать электронные таблицы, которые имитируют макет вашей таблицы и заполняют их данными. Это разоблачит любые слабости, которые могут существовать.
— Майкл Райли - AKA Gunny

Как вы будете указывать внешние ключи на разные продукты, если они находятся в разных таблицах? Читайте о наследовании таблицы, пожалуйста.
— Нил Макгиган

Ответы:


8

Если бы это было мое дизайнерское решение, я бы, вероятно, выбрал больше «Вариант C» (модифицированный вариант a).

Во-первых, почему бы не «Вариант B»:

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

С другой стороны, стратегия индексирования всегда требует, чтобы это поле типа было указано в списке. Так как это всего 4 типа, количество элементов индекса крайне низкое ( SELECT * FROM product_table WHERE type='X'в любом случае, в основном выполняется полное сканирование таблицы)

Вариант С

  • Создайте родительскую таблицу, которая содержит только столбцы, которые разделяют все типы
  • Создайте каждый тип продукта как отдельную таблицу со своими отдельными столбцами, с одним дополнительным: ссылка на родительскую таблицу
  • Создайте каждую таблицу ссылок: Product_Option, Model_option и т. Д. Со ссылками на соответствующие ключи.
  • Для тех, у кого есть взаимные ссылки (MODEL_OPTION, OPTION_MODEL), также создайте эти таблицы. Это добавит ясности в ваши объединения для всех, кто на это смотрит.

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


5
Сейчас есть только 4 типа, но что, если больше будет добавлено позже? Я уверен, что главная таблица продуктов Amazon изначально называлась «Книги», но вы думаете, что у них есть отдельная таблица для каждого типа продукта сейчас? Я не думаю, что у каждого типа должна быть своя собственная таблица, но вы можете использовать модель EAV для дополнительных свойств, которые могут быть общими для каждого типа.
— Аарон Бертран

1
@ Аарон Справедливое замечание о будущем увеличении типов продуктов. Если бы этот сценарий мог предположительно расшириться до 10+ типов продуктов, я бы пересмотрел. Но я считаю, что конкретные таблицы продуктов - это правильный выбор дизайна для небольшого количества типов продуктов.
— Дерек Дауни

1
Вариант C: Нужно ли иметь таблицу ссылок? Я предположил бы, что PK Product_Option будет соответствовать PK таблицы Product, и это создаст ассоциацию для связи обеих таблиц.
— Выплата

Используя Product_option в качестве примера, схема будет (на мой взгляд): id, productID, optionID. productIDбудет FK для product.id, и optionIDявляется FK для option.id. Вот что я имел в виду под таблицей ссылок. И да, в этом проекте необходимо разрешить одному продукту ссылаться на несколько вариантов.
— Дерек Дауни

Хорошо я понял. Я неправильно понял, что вы напечатали .. Ой.
— Выплата

7

Я бы посоветовал вам начать с «правильной» реляционной модели, вашего варианта А. Если типичное использование этой модели ведет вас к денормализации в некоторых областях, не бойтесь делать это.

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

Если интерфейс к базе данных хорошо спроектирован, то ничто не мешает вам адаптировать схему, когда вы узнаете больше о моделях использования систем.


2

Это звучит очень похоже на Bills материалов / нескольких кардинальностей heirarcy , что Пол Нильсен описывает в главе 17 из SQL Server 2008 Библии .

Вся глава очень хорошо прочитана, а конкретный раздел, посвященный вашей проблеме «многие ко многим», можно найти на страницах 416–419.

Это лучшее обсуждение, которое я видел в отношении типа данных с разнесенными частями .


Это решение выглядит аналогично варианту B (если я правильно понимаю, что я не уверен, что я понимаю). У меня была бы основная таблица (Products) и таблица «link» (также называемая смежной таблицей / BillsofMaterials) для создания связей между моделями, опциями, наборами и т. Д. Это правильно?
— Payling

Я думаю, что проблема затуманена из-за вариантов. Давайте возьмем варианты из обсуждения на некоторое время. Части самые маленькие. Группа деталей составляет модель. Группа запасных частей в форме комплекта составляет подмножество модели. Все идет нормально. Теперь у деталей есть опции, для простоты предположим, что это включает две категории: цвет (черный, красный, хром) и материал (металл, дерево, пластик). Вы также упомянули, что у моделей есть варианты. Параметры модели отделены от параметров детали или модели кажутся имеющими только варианты, потому что детали отличают модели?
— Майкл Райли - AKA Gunny

Запчасти не имеют «вариантов» в моем дизайне. Я определяю опцию как нечто, что входит в модель, которая предоставляет ему расширенную функциональность. Опция состоит из частей. Модель может иметь много разных вариантов. Опция может подходить для многих моделей.
— оплата

Это не так, как вы сформулировали свой вопрос. Цитата: «Например, у Модели может быть много опций, а у опции может быть много моделей. У опции также может быть много деталей, и у детали может быть много опций ... и так далее ..." В этом пункте я предлагаю вам создавать электронные таблицы, которые имитируют макет вашей таблицы и заполнять их данными. Это разоблачит любые слабости, которые могут существовать.
— Майкл Райли - AKA Gunny

0

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

Вместо того, чтобы оставлять много неиспользуемых пустых полей в таблице Product, почему бы не добавить таблицу ModelProduct, таблицу PartProduct, таблицу ReplacementPartKitProduct и иметь только те поля, которые различны для этих типов в этих таблицах? Используйте для этих таблиц тот же первичный ключ, что и для таблицы Product. Присоединитесь к таблице Product и ModelProduct, если вы хотите работать с моделями. Нужно определить, является ли запись Продукта вашей Частью? Просто выполните левое соединение между Product и PartProduct, и если PartProduct. [PrimaryKey] не равен NULL, у вас есть деталь. Если это ноль, это не часть. Кроме того, вы можете добавить поле ProductType в таблицу Product.


Пустые поля будут минимальными, потому что примерно 75% полей будут использоваться в каждой таблице. Думаю, меня больше беспокоит связь между типами продуктов. У меня будет три или около того таблицы ссылок, указывающих на одну и ту же таблицу. Model_has_Option два первичных ключа, оба идентификатора продукта таблицы продуктов, если бы я использовал только одну таблицу для представления типов продуктов. Меня больше волнует, правильно ли это делать или нет.
— выплаты

Хотя существует много факторов, которые влияют на «правильное» решение, необходимо учитывать два основных фактора. 1: общие требования к производительности; 2: адаптивность / сложность / ремонтопригодность. Один из этих двух, вероятно, немного важнее другого. Если вам нужна скорость, денормализуйте, придерживаясь варианта А. У вас будет дублирование; это ожидается. Если вам нужно регулярно работать со схемой, а скорость - это НЕ САМЫЙ важный фактор, тогда Вариант B. Вы понимаете это «правильно», зная свои приоритеты, а не придерживаясь «чужих лучших практик».
— Алан Макби
Используя наш сайт, вы подтверждаете, что прочитали и поняли нашу Политику в отношении файлов cookie и Политику конфиденциальности.
Licensed under cc by-sa 3.0 with attribution required.