你知道为什么这个请求会很慢吗(在其他快速的MySQL服务器上是1.7秒):
SELECT DISTINCT TABLE_A.keyA
FROM TABLE_A,TABLE_B
WHERE TABLE_A.keyB= TABLE_B.keyB
AND TABLE_A.fieldC in (0,2,5,7,8) LIMIT 20;
使用EXPLAIN
给出的执行计划:
id select_type table type possible_keys key key_len ref rows Extra
1 SIMPLE TABLE_B index PRIMARY PRIMARY 8 NULL 10 Using index; Using temporary
1 SIMPLE TABLE_A ref IDX_TABLE_A_KEY_B IDX_TABLE_A_KEY_B 8 TABLE_B.keyB 25455 Using where
其他元素:
- 表TABLE_A有30万行
- TABLE_A。keyA是TABLE_A 的主键。
- TABLE_A。keyB是指向TABLE_B的主键keyB的外键;表TABLE_B有10行;
- 99%的TABLE_A有fieldC=1, 1%的表有fieldC在(0,2,5,7,8)(这就是为什么这个字段没有被索引;编辑这个子句没有问题,因为使用相同的子句但不与TABLE_B连接的SELECT是快速的);
- 在我看来,是JOIN出错了,因为在表上执行简单的SELECT操作速度很快;
- 与另一个表TABLE_C的连接也很慢; MySQL版本:5.1.23a-maria-alpha
你知道吗?
99%的TABLE_A有fieldC=1, 1%的表有fieldC在(0,2,5,7,8)(这就是为什么这个字段没有被索引
这将是索引列的一个很好的理由。您的查询只需要不到1%的表,因此索引将是非常有选择性的。
可能是IN
子句,它们往往很慢,你有TABLE_A.fieldC
的索引吗?
SELECT DISTINCT TABLE_A.keyA
FROM TABLE_A
INNER JOIN TABLE_B ON TABLE_A.keyB = TABLE_B.keyB
WHERE
TABLE_A.fieldC IN (0, 2, 5, 7, 8) LIMIT 20;
try
SELECT DISTINCT TABLE_A.keyA
FROM TABLE_A
WHERE TABLE_A.keyB IN (SELECT TABLE_B.keyB FROM TABLE_B )
AND TABLE_A.fieldC in (0,2,5,7,8) LIMIT 20;
为列fieldC添加索引。然后运行查询
Select DISTINCT keyA from
(select keyA, keyB from TABLE_A where fieldC in (0,2,5,7,8))
as temp STRAIGHT_JOIN TABLE_B on temp.keyB=TABLE_B.keyB limit 20