multiple-join-and-or-in-where子句mysql查询优化

iqjalb3h  于 2021-08-09  发布在  Java
关注(0)|答案(1)|浏览(353)

我正在尝试优化一个与此类似的查询:

SELECT * FROM table1 t1 INNER JOIN table2 t2 ON t1.t2_id = t2.id
LEFT OUTER JOIN table3 t3 ON t1.t3_id = t3.id
LEFT OUTER JOIN table4 t4 ON t3.t4_id = t4.id
LEFT OUTER JOIN table5 t5 ON t3.t5_id = t5.id
LEFT OUTER JOIN table6 t6 ON t1.t6_id = t6.id
WHERE (t1.attribute1 = ? OR t2.attribute2 = ?)
AND t1.active = 1
AND t1.status <> 10

我在日志中看到,使用最多的是where子句中的or(使用or时,查询的执行时间约为1s,而使用我从db中采样的数据时,查询的执行时间约为400ms)。
我正在寻找替代方法来获得相同的结果,而不需要花费太多时间(而且,如果同时执行许多查询,性能会下降)。
我尝试过用联合子查询替换or,并在t1和t2之间建立连接(我正在使用mysql 5.7):

SELECT * FROM (SELECT * FROM table1 t1 INNER JOIN table2 t2 ON t1.t2_id = t2.id
WHERE t1.attribute1 = ?
UNION
SELECT * FROM table1 t1 INNER JOIN table2 t2 ON t1.t2_id = t2.id
WHERE t2.attribute2 = ?
) AS joined
LEFT OUTER JOIN table3 t3 ON joined.t3_id = t3.id
LEFT OUTER JOIN table4 t4 ON t3.t4_id = t4.id
LEFT OUTER JOIN table5 t5 ON t3.t5_id = t5.id
LEFT OUTER JOIN table6 t6 ON joined.t6_id = t6.id
WHERE joined.active = 1
AND joined.status <> 10

但是我想知道是否有更好的方法来优化查询。
编辑:active、status、attribute1和attribute2与id一起被索引。

gpnt7bae

gpnt7bae1#

以下索引可以提高第一个查询的性能,只要您选择的行不太多(理想情况下少于1000行):

create index ix1 on table1 (attribute1, active, status, t2_id);

添加此索引。如果仍然很慢,在你的问题中加入执行计划。

相关问题