问题 使用mysql ENUM是一个糟糕的架构解决方案吗?


对我来说,就像在应用程序代码中使用硬编码值而不是常量变量一样。但那里有不同的意见。所以我无法确定。

附:对于这个问题的范围,我们假设性能不是问题。


4206
2018-05-14 15:49


起源



答案:


这取决于你想要实现的目标。如果你说的性能不是问题,那么它在很大程度上取决于你的理念,以及数据固有的可变性。如果您使用ENUM存储一周中的数值,以帮助人类可读性和数据的“可查询性”,那么它是完全有效的用途(在某些情况下,使用数字或其他方面更优越)表示)。但是,如果您使用它来存储产品所属的类别(可用类别集可能很容易改变),那么这是一个非常糟糕的解决方案。


8
2018-05-14 15:51



实际缺点是可扩展性。如果不更新整个表,则无法向列表中添加值。您无法将值标记为历史值。值列表是有限的。虽然在将列表功能移动到应用程序的MVC模型并让列类型为CHAR时,您可以充分利用这两者。除非性能和存储对您的应用程序都很关键,否则当数据库仅由应用程序使用时,我不建议使用枚举。 - Code4R7


答案:


这取决于你想要实现的目标。如果你说的性能不是问题,那么它在很大程度上取决于你的理念,以及数据固有的可变性。如果您使用ENUM存储一周中的数值,以帮助人类可读性和数据的“可查询性”,那么它是完全有效的用途(在某些情况下,使用数字或其他方面更优越)表示)。但是,如果您使用它来存储产品所属的类别(可用类别集可能很容易改变),那么这是一个非常糟糕的解决方案。


8
2018-05-14 15:51



实际缺点是可扩展性。如果不更新整个表,则无法向列表中添加值。您无法将值标记为历史值。值列表是有限的。虽然在将列表功能移动到应用程序的MVC模型并让列类型为CHAR时,您可以充分利用这两者。除非性能和存储对您的应用程序都很关键,否则当数据库仅由应用程序使用时,我不建议使用枚举。 - Code4R7


这在很大程度上取决于实际情况,但首先是列类型的要点是精确定义哪些值是允许的,哪些不是。如果在您的问题域中,您要考虑存储为ENUM值的属性是 固定 从某种意义上说,它不可能有其他价值,那么ENUM是一个很好的选择。一个例子是性别: ENUM('male', 'female') 是伟大的,因为第三性别的可能性确实很低。

如果要存储更有可能更改的值,则可以考虑将数据模型规范化为多对一关系。


2
2018-05-14 15:55



假设您必须将其翻译成另一种语言,或者假设业务要求您接受“M”和“F”。 - MattK
@MattK这些是应用程序/接口问题,而不是数据问题。 - molf
我明白你在说什么,但ENUM已经将界面与数据混合在了一起。如果我们想要这个纯数据,那么只需使用0和1。如果您希望您的数据库具有更易读的内容(例如“男性”和“女性”),那么未来是否需要更改数据(例如国际化)? - MattK
0或1都不是男性或女性。没有应用程序,您无法理解数据。这是使用幻数而不是ENUM的缺点(确切地说它是如何在代码中)。 - molf
当然,但这只是您定义应用程序的位置问题。在数据库的模式中,数据库中的数据或单独的应用程序层中的数据。 MySQL允许您将此信息存储在架构层中,这在很多方面是最麻烦且最不灵活的地方。有一个原因是ENUM不是ANSI SQL特性,大多数其他数据库系统也不支持。 - MattK


不管怎样!它们比数字字段有几个优点:

  • 它们更具可读性:UPDATE Person SET state = 2 - 2代表什么?
  • 它们的范围有限:如果一个人只有10个状态,为什么允许数值11+?
  • 它们可以像它们的数字计数器部分一样使用:UPDATE person SET state = state + 1

实际上,使用数值而不是枚举就像将常量放入源代码中一样。


2
2018-05-14 15:59





ENUM非常适合您知道属于静态集的数据。

如果您使用的是Mysql 5+,则存储 几乎总是更好 正如MySQL官方参考资料所示,静态集中的数据采用ENUM类型。更不用说数据是可读的,并且您有额外的验证层。

如果您想知道使用ENUM是否是我推荐使用的优化 程序分析。这将为您的列推荐正确的数据类型。


2
2018-04-10 15:54