整形数字と文字列数字のインデックス使用状況
2064 ワード
文の準備:
mysqlは整形と文字列の間で数字を自動的に変換します!次の2つの文の結果は同じです:SELECT*FROM ix_test WHERE id_1=1;SELECT * FROM ix_test WHERE id_1='1';
しかしインデックスの使用状況では、結果は全く違います!1つ目はインデックスを使用しません.2つ目はインデックスを使用します.
2つの文、1つ目はインデックスを使用していますが、全テーブルをスキャンし、2つ目はデータに直接インデックスし、1行だけ読み込む必要があります.
でもid_1フィールドが整形になり、後で整形や文字列でマッチングするにはインデックスを使用し、インデックスが直接ヒットします.
だから、どんなにお父さんのmysql sqlオプティマイザ、どんなに痛い悟り!
whereの後ろのフィールドタイプが文字列の数字に対して、整形で一致(つまり引用符で数字を引かない)すると、インデックスから直接命中することができず、すべてのスキャンが必要になると結論した.
特に注意が必要!
DROP TABLE ix_test;
CREATE TABLE ix_test
(id_1 varchar(20) NOT NULL,
PRIMARY KEY(id_1));
INSERT INTO ix_test VALUES (1),(2),(3),(4),(5),(6),(7),(8),(9),(10),(11);
mysqlは整形と文字列の間で数字を自動的に変換します!次の2つの文の結果は同じです:SELECT*FROM ix_test WHERE id_1=1;SELECT * FROM ix_test WHERE id_1='1';
しかしインデックスの使用状況では、結果は全く違います!1つ目はインデックスを使用しません.2つ目はインデックスを使用します.
2つの文、1つ目はインデックスを使用していますが、全テーブルをスキャンし、2つ目はデータに直接インデックスし、1行だけ読み込む必要があります.
mysql> explain select * from ix_test where id_1=1;
+----+-------------+---------+-------+---------------+---------+---------+------+------+--------------------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+---------+-------+---------------+---------+---------+------+------+--------------------------+
| 1 | SIMPLE | ix_test | index | PRIMARY | PRIMARY | 302 | NULL | 11 | Using where; Using index |
+----+-------------+---------+-------+---------------+---------+---------+------+------+--------------------------+
1 row in set (0.00 sec)
mysql> explain select * from ix_test where id_1='1';
+----+-------------+---------+-------+---------------+---------+---------+-------+------+-------------+
| id | select_type | table | type | possible_keys | key | key_len | ref | rows | Extra |
+----+-------------+---------+-------+---------------+---------+---------+-------+------+-------------+
| 1 | SIMPLE | ix_test | const | PRIMARY | PRIMARY | 302 | const | 1 | Using index |
+----+-------------+---------+-------+---------------+---------+---------+-------+------+-------------+
1 row in set (0.01 sec)
でもid_1フィールドが整形になり、後で整形や文字列でマッチングするにはインデックスを使用し、インデックスが直接ヒットします.
だから、どんなにお父さんのmysql sqlオプティマイザ、どんなに痛い悟り!
whereの後ろのフィールドタイプが文字列の数字に対して、整形で一致(つまり引用符で数字を引かない)すると、インデックスから直接命中することができず、すべてのスキャンが必要になると結論した.
特に注意が必要!