更快地选择查询多个主键

时间:2018-10-12 12:49:23

标签: mysql sql database select

在测试我的简单邮件MySQL数据库时,我发现了一个奇怪的行为,并且很高兴知道为什么。

我的“邮件”表有两个主键:

idx : INT(Auto-Increment)
uid : VARCHAR(50)

以及其他一些哑列,例如createdTime,info等。

然后,我用200,000个伪数据填充了我的表,并通过一个简单的搜索查询进行了测试:

SELECT * FROM mail WHERE uid='RANDOMGENERATEDUID';

执行此查询大约需要0.235秒,从工作台的表格说明中,我发现该查询执行全表扫描并且不使用任何键。

我很好奇,如果我 force 对SELECT查询使用'idx'列会发生什么,所以,我测试了另一个查询,该查询将具有相同的结果:

SELECT * FROM mail
WHERE idx IN (SELECT idx FROM foodwagondb.mail WHERE uid='RANDOMGENERATEDUID');

但是令我惊讶的是,该查询的执行速度更快,执行时间仅为0.078秒!

在这里我的眼睛后面发生了什么?我很高兴知道为什么会这样!

2 个答案:

答案 0 :(得分:0)

您应避免使用IN子句,而应使用INNER JOIN

SELECT m1.* FROM mail m1
INNER JOIN foodwagondb.mail m2 ON m2.idx = m1.idx 
WHERE idx m2.uid='RANDOMGENERATEDUID';

IN子句等效于OR条件,这意味着针对每个值重复执行相关查询。内部联接仅执行查询并匹配结果值。

无论如何,您都可以使用适当的uid到

复合索引来改善这两个查询
create index my_index on mail (uid, idx)

答案 1 :(得分:0)

在第一个查询中,您基于varchar字段(uid)搜索每一行。 在第二个查询中,mysql根据索引字段(idx)预先过滤行,然后在该子集中搜索文本字符串。对于较小的表,您看不到差异,但是对于较大的表,它会降低性能。 @scaisEdge是正确的,INNER JOIN规则!