CREATE TABLE `files` (
`did` int(10) unsigned NOT NULL DEFAULT '0',
`filename` varbinary(200) NOT NULL,
`ext` varbinary(5) DEFAULT NULL,
`fsize` double DEFAULT NULL,
`filetime` datetime DEFAULT NULL,
PRIMARY KEY (`did`,`filename`),
KEY `fe` (`filetime`,`ext`), -- This?
KEY `ef` (`ext`,`filetime`) -- or This?
) ENGINE=InnoDB DEFAULT CHARSET=utf8 ;
表中有一百万行。文件时间基本上是不同的。数量有限的 ext
价值观。所以, filetime
有很高的基数和 ext
基数要低得多。
查询涉及两个方面 ext
以及 filetime
:
WHERE ext = '...'
AND filetime BETWEEN ... AND ...
这两个指标哪一个更好?为什么?
1条答案
按热度按时间eufgjt7s1#
首先,让我们试试
FORCE INDEX
选择其中一个ef
或者fe
. 时间太短,无法清楚地了解哪个更快,但“解释”显示了不同:强制范围打开
filetime
首先(注:订单WHERE
没有影响。)强制低基数
ext
第一:显然
rows
说ef
这样更好。但是让我们检查一下优化器跟踪。产量相当庞大;我只展示有趣的部分。不FORCE
是需要的;跟踪将显示两个选项,然后选择更好的。...
...
与
fe
(首先是range列),可以使用range,但它估计扫描16684行以获取ext='gif'
.与
ef
(低基数)ext
首先),它可以使用索引的两列,并在btree中更有效地向下钻取。然后它发现了大约538行,所有这些行都对查询有用——不需要进一步过滤。结论:
INDEX(filetime, ext)
仅使用第一列。INDEX(ext, filetime)
使用了两列。将涉及的列放入
=
首先在索引中进行测试,而不考虑基数。查询计划不会超出第一个“range”列。
“基数”与复合索引和此类查询无关。
(“使用索引条件”意味着存储引擎(innodb)将使用除用于过滤的索引列之外的索引列。)