我有一个个人资料页面,上面有大约 20 个可选字段。为了保持规范化,我必须创建 20 个不同的表,然后在其中进行 20 个查询JOINS
。这对我来说似乎有点过头了。
这是最好的方法吗?
你建议我保持正常化吗?
我有一个个人资料页面,上面有大约 20 个可选字段。为了保持规范化,我必须创建 20 个不同的表,然后在其中进行 20 个查询JOINS
。这对我来说似乎有点过头了。
这是最好的方法吗?
你建议我保持正常化吗?
做到这一点的一个好方法(虽然有点混乱,除非你知道发生了什么)是使用相同的设计 wordpress 使用 - 据我所知,它被称为实体属性值(感谢@Matt Fenwick)。https://stackoverflow.com/tags/eav/info
基本的想法是INNER JOIN
,你有两张桌子,而不是你的 20 张桌子来存储零碎的东西。一个存储您的实体(wordpress 案例中的一个帖子),第二个存储您所有的零碎物品 - 或 WP 所指的元数据。您不必为每个数据点设置一列,而是有一列用于名称,一列用于值,一列用于该属性适用的实体的 ID。
通过这种方式,您可以节省大量 SQL、扩展过程中的麻烦以及开始构建它所需的时间。如果您需要满足另一个属性,您只需将其与其余部分一起放入其中 - 无需破解模式。
关于 WP 数据库布局的更多细节(这里我主要考虑 wp_posts 和 wp_postmeta 表):http ://codex.wordpress.org/Database_Description
所以一个例子可能是(伪代码,对不起):
table: yourEntity
entityID int, primary key, auto increment
title varchar
table: yourEntityMeta
entityID int, non-unique key
name text
value text
通过这种方式,您可以为每个实体拥有任意数量的属性,而对未使用的具有NULL
值的列和需要连接的 18 个表没有任何限制或性能问题。
希望这可以帮助
注意:其中一个问题(@ypercube 在评论中指出)是使用这意味着您不能为每个属性指定数据类型,即日期属性将存储为文本,布尔值或整数也是如此。您也无法使用外键链接到有效值表(感谢@Catcall)。在沿着这条路线走之前,您需要仔细考虑这一点。
我只会对可选字段使用可为空的列。该表会变得非常大,但是如此多的连接只会降低您的性能,如果这些字段属于一个对象并且将一起更新,我找不到应该规范化这些字段的原因。
如果选项字段是常量,请考虑使用 ENUM(用于 2-20 个选项),但是这种方法有其自身的缺陷。
如果您主要关心的是数据库规范化,那么即使您有 20 个选项字段,您也应该为每个选项字段提供单独的“查找”表,这样您就不会存储重复数据。
此外,如果您决定在将来更改选项,它会使您的表在将来更容易维护。
JOIN 语句还不错,MySQL 一次查询最多可以支持 61 个表。我已经在我的这个问题中探讨了这个话题。