我有大型数据库(数百万行),我正在尝试为2个字段的数据类型做出最佳选择。我做的大部分都是varchar或INT。然而,2个领域我想知道Enum是否是最好的方式。
领域1
第一个字段是性别,我的数据目前是“男性”或“女性”,或者可能是
空白。我最初设置如下:
GENDER VARCHAR(6) NOT NULL
这是最好的方式,还是最好将其设置为:
GENDER ENUM ('Male', 'Female') NOT NULL
我是否需要将其设为非空以允许空白,或者我是否需要添加空白,即
GENDER ENUM ('Male', 'Female', '') NOT NULL
更不用说了,我正在考虑将整个领域转换为M或F.
领域2:
我有几乎相同的事情需要考虑,除了状态字段,可能包括52个值(50个状态,DC,加上空白)。
我想最大的问题是 - 所有这些Enum的东西都值得吗?我的数据库有数百万行,所以一切都是一个因素,但我应该只使用VARCHAR(2)作为状态而不是ENUM。
我经常适用于这种情况的经验法则是不使用MySQL ENUM。使用它们会产生维护问题,尤其是在添加/删除/重命名某些值时。在InnoDB中,重命名和删除枚举值在大表上很重要。不添加值(只要您不在中间添加它)。
由于您可能希望将此列保留在上下文中,并且不允许任何值超出此上下文,因此IMHO最好使用INT,并将其作为外键连接到值表(列id,值)。
您可以轻松地在此表中添加和重命名值,在删除值之前,FK将强制处理主表中具有此值的任何现有记录。
要轻松读取数据,您只需要一个简单的JOIN即可。
注意:由于性别是最终的,你可能想把它保留为VARCHAR(1)或使用像Johan建议的ENUM,但谁知道呢?您可能希望将来支持跨性别者和双性化。不开玩笑。
我经常适用于这种情况的经验法则是不使用MySQL ENUM。使用它们会产生维护问题,尤其是在添加/删除/重命名某些值时。在InnoDB中,重命名和删除枚举值在大表上很重要。不添加值(只要您不在中间添加它)。
由于您可能希望将此列保留在上下文中,并且不允许任何值超出此上下文,因此IMHO最好使用INT,并将其作为外键连接到值表(列id,值)。
您可以轻松地在此表中添加和重命名值,在删除值之前,FK将强制处理主表中具有此值的任何现有记录。
要轻松读取数据,您只需要一个简单的JOIN即可。
注意:由于性别是最终的,你可能想把它保留为VARCHAR(1)或使用像Johan建议的ENUM,但谁知道呢?您可能希望将来支持跨性别者和双性化。不开玩笑。
如果你想拥有一个值 no value entered
, 使用 null
那是什么 null
是专为!
如果你想在男性和女性之间指定一些东西(一些不幸的人有这种情况),请使用
ENUM('male','female','neither') NULL;
请注意,枚举确实如此 不 将文字文本值存储在列中。
male
存储为1, female
作为2和 neither
如3等
这意味着它比varchar更有效。
如果你正在努力 null
在您的选择中,请注意您可以使用 ifnull
要么 coalesce
功能来取代 null
用更有用的东西。
SELECT IFNULL(gender,'unknown') as gender FROM people;
-- or the identical statement
SELECT COALESCE(gender,'unknown') as gender FROM people;