ぶろぐ

日記です

in句に型が混合しているとインデックスが効かない


という話を聞いたので、一応検証しておいた。

mysql> explain select * from page where page_id in (1,2,3,4);
+----+-------------+-------+-------+---------------+---------+---------+------+------+-------------+
| id | select_type | table | type  | possible_keys | key     | key_len | ref  | rows | Extra       |
+----+-------------+-------+-------+---------------+---------+---------+------+------+-------------+
|  1 | SIMPLE      | page  | range | PRIMARY       | PRIMARY | 4       | NULL |    4 | Using where |
+----+-------------+-------+-------+---------------+---------+---------+------+------+-------------+
1 row in set (0.03 sec)

mysql> explain select * from page where page_id in ("1",2,3,4);
+----+-------------+-------+------+---------------+------+---------+------+---------+-------------+
| id | select_type | table | type | possible_keys | key  | key_len | ref  | rows    | Extra       |
+----+-------------+-------+------+---------------+------+---------+------+---------+-------------+
|  1 | SIMPLE      | page  | ALL  | PRIMARY       | NULL | NULL    | NULL | 1676425 | Using where |
+----+-------------+-------+------+---------------+------+---------+------+---------+-------------+
1 row in set (0.00 sec)

本当だった。
ちなみにin句使う場合だけっぽい。

--これ効く
explain select * from page where page_id = "1" or page_id = 2 or page_id = 3 or page_id = 4;
--これ効かない
explain select * from page where page_id in ("1",2,3,4);

ORMにラップされて数値型と文字列型が混合したSQLを投げてることに気づかずにslow_queryが溜まりまくる、という事案があったらすい。
possible_keysにはあげられているので、mysqlの気分次第で使われることもある…?