我有这个问题不是我写的,我必须优化:
SELECT DISTINCT r.itemid
, r.catid
, i.title
, i.owner
, i.image
, i.background
, i.icon
FROM jos_sobi2_cat_items_relations r
LEFT
JOIN jos_sobi2_item i
ON i.itemid = r.itemid
WHERE
( i.published = 1
AND r.catid > 1
AND ( i.publish_down > '2016-10-26 13:08:02'
OR i.publish_down = '0000-00-00 00:00:00'
)
AND i.itemid IN ( SELECT itemid
FROM jos_sobi2_item
WHERE ( published = 1
AND ( publish_down > '2016-10-26 13:08:02'
OR publish_down = '0000-00-00 00:00:00'
)
)
)
)
GROUP
BY i.itemid
ORDER
BY i.publish_up DESC
LIMIT 0,14
这是解释mysql命令:
“items”表确实只有itemid字段的主键。 “关系”表确实有以下3个索引:
- catid,itemid PRIMARY BTREE
- itemid BTREE
- catid BTREE
我看到如果删除DISTINCT或GROUP BY子句,查询速度很快,否则执行时间超过1分钟。
我首先想到的是删除DISTINCT子句,因为GROUP BY子句已经完成了这项工作。但我不确定。
有关如何优化它的任何帮助吗?
感谢。
答案 0 :(得分:0)
首先,items.itemid IN(...)是多余的,您已经在查询中拥有这些条件。你不需要LEFT JOIN,项目行在where条件下,它不能丢失。您不需要distinct或group by,[relation.itemid,relation.catid]是主键,它不能包含重复项。结果是:
SELECT relation.itemid, relation.catid, title, owner, image, background, icon FROM
`jos_sobi2_cat_items_relations` AS relation
JOIN `jos_sobi2_item` AS items ON relation.itemid = items.itemid WHERE
`published` = '1' AND
relation.catid > 1 AND
(`publish_down` > '2016-10-26 13:08:02' OR `publish_down` = '0000-00-00 00:00:00' )
ORDER BY items.publish_up DESC, relation.itemid, relation.catid LIMIT 0, 14
您可以将结果与原始查询进行比较。我在relation.itemid和relation.catid上添加了顺序,以便结果是确定性的。您可以在items.publish_up上添加索引,以便在需要时加快查询速度。