MySQL会为NULL值建立索引吗?

83

我有一个MySQL表格,其中一个索引的INT列90%的行将为0。如果我将这些行改为使用NULL而不是0,它们会被排除在索引之外,使索引减少约90%吗?

5个回答

38

4
请注意,文档中提到了一些注意事项,例如“优化只能处理一个IS NULL”。 - Timo

11

看起来它确实也会索引 NULL 值。

运行此操作时要小心,因为MySQL在创建索引时会锁定表以进行写操作。即使该列为空(全部为null),构建索引也可能需要很长时间。

参考链接


2
你是怎么得出那个结论的?我没有看到任何关于这个主题的提及。 - too much php
这是在文章底部的评论中提到的。我提取了相关部分。 - Bill the Lizard
7
我认为处理大表数据需要一些时间是因为 MySQL 需要扫描整个表,而不是因为它在构建巨大的索引。我可能错了。 - too much php
3
是的,实际上,“在大表上需要一些时间……即使列都是空的”可以理解为“处理空值很快[因为它们未被索引],但如果表很大……”请注意,我的翻译尽可能保持原文意思,并使其更通俗易懂。 - KajMagnus

3

允许一个列为空将会增加该列的存储需求一个字节。这将导致索引大小增加,可能不太好。但是,如果您的查询大量使用“IS NULL”或“NOT NULL”,它们可能比进行值比较更快。

我的直觉告诉我应该选择非空,但有一个答案:测试!


1
问题是索引是否会增加大小。答案是第二句话将增加索引大小。 - J.D. Fitz.Gerald
3
“标题”询问MySQL是否索引空列(它确实这样做)。 “描述”似乎提出了一个稍微不同的问题,但实际上只是阐明为什么首先提出了(标题)问题。此外,由于人们大多根据标题选择是否阅读问题,在大多数情况下,我会说标题形式优先于描述形式。 - user359996
2
此外,允许空列会向添加一个字节,而不是列,除非已经有(8的倍数)可空列,因为空值被位图化。实际上,这可以很好地节省空间,因为只需要在位图中存储空值。 - user359996
2
在这种情况下,一个整数列90%的时间为NULL,90%的时间只需要1个或更少的字节,而10%的时间需要4到5个字节。平均而言,这比始终不允许NULL时的4个字节显着少。 - user359996

1
每个索引都有一个基数,表示有多少个不同的值被索引。据我所知,说索引在许多行中重复相同的值并不是一个合理的想法,但是索引只会将重复的值寻址到许多行的聚集索引上(具有此字段的空值的行),并保留聚集索引的参考ID,这意味着:每个具有NULL值索引字段的行浪费了与PK一样大的空间(因此专家建议如果您有组合PK,请使用合理的PK大小)。

1

不会,它将继续包含它们,但不要对任何一种情况的后果做出太多假设。很多事情取决于其他值的范围(可以在谷歌上搜索“基数”)。

MSSQL有一种新的索引类型,称为“过滤索引”,用于这种类型的情况(即根据过滤器在索引中包含记录)。类似的功能曾经在dBASE类型的系统中存在过,非常方便。


网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接