0

我有一个m_idx关于(k1,k2,k3)
If I do
SELECT c1,c2,c3... FROM tb FORCE INDEX (m_idx) WHERE k1=500 AND k2 IN(...) AND k2>2000 ORDER BY k1 LIMIT 1000;
OR
SELECT c1,c2,c3... FROM tb FORCE INDEX (m_idx) WHERE k1 IN (500,1000,1500 ...) AND k2 IN(...) AND k2>2000 ORDER BY k1 LIMIT 1000;
Handler_read_next = 999 的索引

但是如果我尝试在 k1 上使用一个范围:
SELECT c1,c2,c3... FROM tb FORCE INDEX (m_idx) WHERE k1>=500 AND k2 IN(...) AND k2>2000 ORDER BY k1 LIMIT 1000;
Handler_read_next = 58035
在所有情况下,EXPLAIN 都说使用的键是m_idx
但我认为在第三种情况下m_idx它没有被使用(我也只有在 k1 上有一个索引)。
否则我不明白为什么它读取的行数超过 1000 行。
我期待扫描m_idx索引,以及ONLY the first 1000从表中读取满足条件的行。
但实际上我认为对于第三种情况,它会扫描索引,从 tb 读取满足 k1 条件的行,在从 tb 读取行后检查 k2 和 k3 条件。
我使用:MySql 和 MyISAM,WINDOWS 7 64,tb 有 1 百万行;
所以我的问题是:
是否可以在最左边的多重索引上按范围进行选择?
或者
我做错了什么?
谢谢你。

4

1 回答 1

0
  1. 不它不是。
  2. 不,你做的一切都是对的

http://dev.mysql.com/doc/refman/5.1/en/range-optimization.html(“7.3.1.3.2 . 多部分索引的范围访问方法”部分)

所以你不能帮助优化器更快地执行这个查询。

并且避免使用FORCE INDEX,因为优化器更清楚要使用什么索引。

还:

k1>=500 AND k2 IN(...) AND k2>2000

根据哪个部分返回较少的记录,k1>=500或者k2 IN(...) AND k2>2000(我不确定您为什么需要> 2000在这里,因为您可以在添加到之前手动比较它IN()),您也可以尝试创建索引k2(如果k2部分返回较少数量的记录)。

于 2010-12-03T01:58:11.933 回答