我有以下查询:
SELECT *
FROM s
JOIN b ON s.borrowerId = b.id
JOIN (
SELECT MIN(id) AS id
FROM tbl
WHERE dealId IS NULL
GROUP BY borrowerId, created
) s2 ON s.id = s2.id
有没有一种简单的方法来优化它,以便我可以直接进行JOIN并利用索引?
更新
created
字段是GROUP BY
语句的一部分,因为由于我们的MySQL版本和使用的ORM的限制,可能有多个具有相同created
的记录时间戳值。因此,我需要找到borrowerId
和created
的每个组合的第一条记录。
通常我会尝试这样的事情:
SELECT *
FROM s
INNER JOIN b ON s.borrowerId = b.id
LEFT OUTER JOIN s2
ON s.borrowerId = s2.borrowerId
AND s.created = s2.created
AND s.id <> s2.id
AND s.id < s2.id
WHERE s2.id IS NULL
AND s.dealId IS NULL;
但我不确定这是否能按我想要的方式运作。
来自MySQL的EXPLAIN输出以下内容:
1 PRIMARY b ALL NULL NULL NULL NULL 129690
1 PRIMARY <derived2> ALL NULL NULL NULL NULL 317751 Using join buffer
1 PRIMARY s eq_ref PRIMARY,borrowerId_2,borrowerId PRIMARY 4 s2.id 1 Using where
2 DERIVED statuses ref dealId dealId 5 183987 Using where; Using temporary; Using filesort
正如您所看到的,它必须查询大量记录以构建子查询数据集,并且在连接到派生子查询时,未找到索引,因此不使用索引。
答案 0 :(得分:0)
第一个查询需要这个复合索引:
INDEX(borrowerId, created, id)
请注意,MySQL很少为一个SELECT
使用两个索引,但复合索引通常非常方便。
第二个查询似乎非常低效。
请为每张表提供SHOW CREATE TABLE
。