是否为不同的产品类型创建单独的表?


25

我正在设计数据库,并且对我的最初设计决策有第二个想法...

产品类型如下...型号,零件,替换零件套件和选件。

选项A(第一种设计):我计划为上述产品类型提供单独的表格。我想说每个表中大约75%的字段是相同的。

由于需要在每个产品类型之间创建关联,因此我将它们创建为单独的表格。例如,一个模型可以有很多选项,而一个选项可以有很多模型。一个选项也可以有很多部分,而一个部分可以有很多选择...等等。

选项B:除了创建单独的表格外,我还可以创建一个名为Product的表格,其中包含模型,零件,备件套件和选件。我可以使用一个称为类型的字段来区分模型,选项等。我认为不利的一面是,某些产品类型永远不会使用多个字段(留空)。我猜这就是“最佳实践”发挥作用的地方。

选项B将大大降低数据库设计的复杂性。在提取查询数据时,我也不必担心引用一堆表...


2
在这一点上,我建议您创建电子表格,以模仿您的表格布局并在其中填充数据。这将暴露可能存在的任何弱点。
迈克尔·赖利

如果外键在不同的表中,您将如何将它们指向不同的产品?请阅读表继承。
尼尔·麦圭根

Answers:


8

如果这是我的设计决定,那么我可能会选择更多的“选项C”(修改后的选项a)。

首先,为什么不选择“选项B”:

一方面,我喜欢每种产品都有自己的桌子所能提供的清晰度。如果只有一张大桌子,上面有一个字段来确定类型,那么关系就不太清楚了。

另一方面,索引策略将始终要求列出该类型字段。由于只有4种类型,因此索引基数非常低(SELECT * FROM product_table WHERE type='X'无论如何基本上都在进行全表扫描)

选项C

  • 创建一个仅包含所有类型共享的列的父表
  • 创建每种产品类型,将它们作为自己的表并包含其各自的列,并额外增加一个:指向父表的链接
  • 创建每个“链接”表:Product_Option,Model_option等,并带有指向各个键的链接。
  • 对于那些具有相互链接的用户(MODEL_OPTION,OPTION_MODEL),请继续创建这些表。这将为任何查看它的人增加连接的清晰度。

缺点是要确保在事物被更新/删除时避免成为孤立的对象,以及最初设计使用这些表的查询的复杂性。


5
现在只有4种类型,但是如果以后再添加更多类型呢?我确定亚马逊的主要产品表最初被称为“书”,但是您认为现在每种产品类型都有单独的表吗?我认为每种类型都不应该有自己的表,但是您可以将EAV模型用于每种类型可能具有的其他附加属性。
亚伦·伯特兰

1
@Aaron关于未来产品类型增加的公平点。如果可以想象这种情况可以扩展到10种以上的产品类型,那么我会重新考虑。但是,我认为特定的产品表是少量产品类型的合理设计选择。
德里克·唐尼

1
选项C:是否需要链接表?我可以想象Product_Option PK将与Product表的PK匹配,并且将创建链接两个表的关联。
支付

以Product_option为例,该模式在我看来是:id,productID,optionID。productID将会是FK product.id,并且optionIDoption.id。这就是链接表的意思。是的,在此设计中必须允许单个产品链接到多个选项。
德里克·唐尼

好,我懂了。我看错了您输入的内容。
支付

7

我建议您从“正确的”关系模型(选项A)开始。如果该模型的典型用法导致您在某些方面趋于非规范化,请不要害怕这样做。

上周,我与一位同事讨论了如何将架构设计通常认为是一成不变的,并且永远无法更改。奇怪,考虑到在应用程序的每个其他层中接受重构的方式如何,重构数据库模式仍然被认为是不切实际的。

如果数据库的接口设计合理,那么当您了解更多有关系统使用模式的信息时,就不会阻止您改编该模式。


2

这听起来非常类似的材料/多基数票据 heirarcy保罗尼尔森介绍了第17章的SQL Server 2008中的圣经

整章内容非常好,第416-419页提供了解决多对多问题的特定部分。

这是我所见过的关于爆炸零件数据设计类型的最佳讨论。


此解决方案看起来与选项B相似(如果我理解正确,则不确定该怎么做)。我要有一个主表(产品)和一个“链接”表(又名相邻表/ BillsofMaterials)来创建模型,选项,套件等之间的关联。对吗?
2011年

我认为,由于选择问题,这个问题已蒙上阴影。让我们从讨论中删除一些选项。零件是最小的单位。一组零件组成一个模型。套件形式的一组替换零件构成了模型的子集。到目前为止,一切都很好。现在,零件具有选项,为简单起见,假设其中包括颜色(黑色,红色,铬)和材料(金属,木材,塑料)两类。您还提到了模型可以选择。是将模型选项与零件选项分开,还是因为零件使模型不同而使模型似乎仅具有选项?
迈克尔·赖利

零件在我的设计中没有“选项”。我将选项定义为在为其提供扩展功能的模型上进行的操作。选项由零件组成。模型可以有许多不同的选择。选项也可以适合许多不同的模型。
支付

那不是你说问题的方式。Quote:“例如,一个模型可以有很多选择,一个选项可以有很多模型。一个选项也可以有很多零件,而一个零件可以有很多选择……依此类推……”在这一点上,我建议你创建可以模仿您的表格布局的电子表格,并在其中填充数据。这将暴露可能存在的任何弱点。
迈克尔·赖利

0

如果您能想象出一种可能的情况,即在这四种产品类型中都有频繁的查询(在我看来,这很可能),那么您的选择B是最好的。

为何不在Product表中保留大量未使用的可空字段,为什么不添加ModelProduct表,PartProduct表,ReplacementPartKitProduct表,并且仅在那些表中具有与这些类型不同的字段?在那些表上使用与Product表相同的主键。当您要使用模型时,请联接Product和ModelProduct表。需要确定您拥有的产品记录是否为零件?只需从Product到PartProduct进行左连接,如果PartProduct。[PrimaryKey]不为null,则您有一个Part。如果为null,则它不是零件。或者,您可以将ProductType字段添加到Product表中。


空字段将是最小的,因为在每个表中将使用大约75%的字段。我想我更担心产品类型之间的关系。我将有三个左右的链接表指向同一张表。如果我仅使用一个表来表示产品类型,则Model_has_Option两个主键都是产品表的产品ID。我更担心这是否正确。
支付

虽然有许多因素会影响“正确”的决定,但有两个要考虑的广泛因素。1:总体性能要求;2:适应性/复杂性/可维护性。这两个中的一个可能比另一个重要。如果需要速度,请坚持使用选项A进行规范化处理。这是预期的。如果您需要定期摆弄架构,而速度不是最重要的因素,那么选择B。通过了解自己的优先级而不是坚持“别人的最佳实践”,可以使它“正确”。
艾伦·麦克比
By using our site, you acknowledge that you have read and understand our Cookie Policy and Privacy Policy.
Licensed under cc by-sa 3.0 with attribution required.