【发布时间】:2020-05-21 18:10:55
【问题描述】:
我有一个不使用索引的 mysql 查询
- 当我使用 system.serial = serials.serial 时,它将使用 system.serial 索引
- 当我使用 system.serial = LEFT(serials.serial,length(serials.serial)-1) 时,它将使用
system.serial 索引 - 当我使用 system.serial = serials.serial 或 system.serial = LEFT(serials.serial,length(serials.serial)-1); 没有使用索引
以下是带有解释结果的查询
谢谢, 瑞恩
示例只有几个联合选择,但实际查询有 ~7k
explain select serials.serial, system.* from
(SELECT 'S244935X7318894' AS 'serial'
UNION SELECT 'S244935X6C39166'
UNION SELECT 'S244911X8121539') as serials
left join system on system.serial = serials.serial;
id;select_type;table;type;possible_keys;key;key_len;ref;rows;Extra
1;PRIMARY;<derived2>;ALL;NULL;NULL;NULL;NULL;2;
1;PRIMARY;system;eq_ref;serial_UNIQUE;serial_UNIQUE;182;serials.serial;1;"Using where"
2;DERIVED;NULL;NULL;NULL;NULL;NULL;NULL;NULL;"No tables used"
3;UNION;NULL;NULL;NULL;NULL;NULL;NULL;NULL;"No tables used"
4;UNION;NULL;NULL;NULL;NULL;NULL;NULL;NULL;"No tables used"
NULL;"UNION RESULT";<union2,3,4>;ALL;NULL;NULL;NULL;NULL;NULL;
explain select serials.serial, system.* from
(SELECT 'S244935X7318894' AS 'serial'
UNION SELECT 'S244935X6C39166'
UNION SELECT 'S315185X9703017'
UNION SELECT 'S384860X9A15080A'
UNION SELECT 'S290000X0307210 A2 BLADE') as serials
left join system on system.serial = LEFT(serials.serial,length(serials.serial)-1) ;
id,select_type,table,type,possible_keys,key,key_len,ref,rows,Extra
1,PRIMARY,<derived2>,ALL,NULL,NULL,NULL,NULL,2,
1,PRIMARY,system,eq_ref,serial_UNIQUE,serial_UNIQUE,182,func,1,"Using where"
2,DERIVED,NULL,NULL,NULL,NULL,NULL,NULL,NULL,"No tables used"
3,UNION,NULL,NULL,NULL,NULL,NULL,NULL,NULL,"No tables used"
4,UNION,NULL,NULL,NULL,NULL,NULL,NULL,NULL,"No tables used"
5,UNION,NULL,NULL,NULL,NULL,NULL,NULL,NULL,"No tables used"
6,UNION,NULL,NULL,NULL,NULL,NULL,NULL,NULL,"No tables used"
NULL,"UNION RESULT","<union2,3,4,5,6>",ALL,NULL,NULL,NULL,NULL,NULL,
explain select serials.serial, system.* from
(SELECT 'S244935X7318894' AS 'serial'
UNION SELECT 'S244935X6C39166'
UNION SELECT 'S244911X8121539') as serials
left join system on system.serial = serials.serial or system.serial = LEFT(serials.serial,length(serials.serial)-1);
id,select_type,table,type,possible_keys,key,key_len,ref,rows,Extra
1,PRIMARY,<derived2>,ALL,NULL,NULL,NULL,NULL,2,
1,PRIMARY,system,ALL,serial_UNIQUE,NULL,NULL,NULL,190694,"Range checked for each record (index map: 0x4)"
2,DERIVED,NULL,NULL,NULL,NULL,NULL,NULL,NULL,"No tables used"
3,UNION,NULL,NULL,NULL,NULL,NULL,NULL,NULL,"No tables used"
4,UNION,NULL,NULL,NULL,NULL,NULL,NULL,NULL,"No tables used"
NULL,"UNION RESULT","<union2,3,4>",ALL,NULL,NULL,NULL,NULL,NULL,
【问题讨论】:
-
是的,你不应该期望 MySQL 引擎支持
IXOR操作。它仍然是一个简单的引擎。 -
我总是参考mysql.rjweb.org/doc.php/index_cookbook_mysql#or 来解决索引问题。我已经有一段时间没有看它了,但是通读它应该可以让您深入了解如何利用索引进行此查询。