[英]MySQL Query optimization with JOIN and COUNT
I have the following MySQL Query:我有以下 MySQL 查询:
SELECT t1.id, t1.releaseid, t1.site, t1.date, t2.pos FROM `tracers` as t1
LEFT JOIN (
SELECT `releaseid`, `date`, COUNT(*) AS `pos`
FROM `tracers` GROUP BY `releaseid`
) AS t2 ON t1.releaseid = t2.releaseid AND t2.date <= t1.date
ORDER BY `date` DESC , `pos` DESC LIMIT 0 , 100
The idea being to select a release and count how many other sites had also released it prior to the recorded date, to get the position.想法是将 select 发布并计算在记录日期之前有多少其他网站也发布了它,以获得 position。
Explain says:解释说:
id select_type table type possible_keys key key_len ref rows Extra
1 PRIMARY t1 ALL NULL NULL NULL NULL 498422 Using temporary; Using filesort
1 PRIMARY <derived2> ALL NULL NULL NULL NULL 91661
2 DERIVED tracers index NULL releaseid 4 NULL 498422
Any suggestions on how to eliminate the Using temporary;关于如何消除 Using 临时的任何建议; Using filesort?
使用文件排序? It takes a loooong time.
这需要很长时间。 The indexes I have thought of and tried haven't helped anything.
我想到并尝试过的索引没有任何帮助。
This answer below maybe not change explain output, however if your major problem is sorting data, which it identified by removing order clause will makes your query run faster , try to sort your subquery join table first and your query will be:下面的这个答案可能不会改变解释 output,但是如果您的主要问题是排序数据,它通过删除 order 子句确定将使您的查询运行得更快,请先尝试对您的子查询连接表进行排序,您的查询将是:
SELECT t1.id, t1.releaseid, t1.site, t1.date, t2.pos FROM `tracers` as t1
LEFT JOIN (
SELECT `releaseid`, `date`, COUNT(*) AS `pos`
FROM `tracers` GROUP BY `releaseid`
ORDER BY `pos` DESC -- additional order
) AS t2 ON t1.releaseid = t2.releaseid AND t2.date <= t1.date
ORDER BY `date` DESC , `pos` DESC LIMIT 0 , 100
Note: My db version is mysql-5.0.96-x64, maybe in another version you get different result.注意:我的数据库版本是 mysql-5.0.96-x64,也许在另一个版本中你会得到不同的结果。
Try adding an index on tracers.releaseid
and one on tracers.date
尝试在
tracers.date
上添加一个索引,在tracers.releaseid
上添加一个
Try having two indices, one on (date)
and one on (releaseid, date)
.尝试有两个索引,一个在
(date)
上,一个在(releaseid, date)
上。
Another thing is that your query does not seem to be doing what you describe it does.另一件事是您的查询似乎没有按照您的描述进行。 Does it actually count correctly?
它实际上计算正确吗?
Try rewriting it as:尝试将其重写为:
SELECT t1.id, t1.releaseid, t1.site, t1.`date`
, COUNT(*) AS pos
FROM tracers AS t1
JOIN tracers AS t2
ON t2.releaseid = t1.releaseid
AND t2.`date` <= t1.`date`
GROUP BY t1.releaseid
ORDER BY t1.`date` DESC
, pos DESC
LIMIT 0 , 100
or as:或作为:
SELECT t1.id, t1.releaseid, t1.site, t1.`date`
, ( SELECT COUNT(*)
FROM tracers AS t2
WHERE t2.releaseid = t1.releaseid
AND t2.`date` <= t1.`date`
) AS pos
FROM tracers AS t1
ORDER BY t1.`date` DESC
, pos DESC
LIMIT 0 , 100
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.