[英]Making SQL query faster
我目前有一个需要很长时间才能加载的SQL查询,想知道是否有人可以帮助我? 我是MySQL的新手。
这是查询:
SELECT applicationid
FROM logs
WHERE action = 'VIEWED'
AND userid = '$user'
AND date >= '$dateminus7'
AND applicationid NOT IN (
SELECT applicationid
FROM logs
WHERE userid = '$user'
AND date >= '$dateminus7'
AND (action LIKE 'SUBMITTED NOTE%' OR action LIKE 'CHANGED STATUS%')
)
基本上,通过一些数据库来查找在访问客户帐户时没有留下笔记的用户(非常顽皮)。 日志数据库中每周大约有30,000条记录,这显然是一个因素,但是现在查询运行了一个小时,但仍未完成(超时,PHP页面上出现404错误)。
只需问任何需要的信息,我将不胜感激任何提示或指示。
(userid, date)
综合索引应足以加快此处的两个查询。 您也可以尝试(userid, date, action)
或(action, userid, date)
。 根据哪一列具有更多唯一值,一个索引可能比另一个索引更有效。
请注意,查询计划程序可能无法优化子查询,并且可能会对外部查询中的每个候选行执行一次子查询。 多次运行内部查询的成本可能会导致性能问题。 考虑改用联接,看看是否能获得更好的性能:
SELECT la.applicationid
FROM logs la
LEFT OUTER JOIN logs lb
ON la.applicationid = lb.applicationid
AND lb.userid = '$user'
AND lb.date >= '$dateminus7'
AND (lb.action LIKE 'SUBMITTED NOTE%' OR lb.action LIKE 'CHANGED STATUS%')
WHERE la.action = 'VIEWED'
AND la.userid = '$user'
AND la.date >= '$dateminus7'
AND lb.applicationid IS NULL;
我发现MySQL不能很好地优化IN
和NOT IN
查询。 用JOIN
替换它们通常可以改善情况。 对于NOT IN
您必须使用LEFT OUTER JOIN
:
SELECT l1.applicationid
FROM logs l1
LEFT OUTER JOIN (SELECT applicationid
FROM logs
WHERE userid = '$user'
AND date >= '$dateminus7'
AND (action LIKE 'SUBMITTED NOTE%' OR action LIKE 'CHANGED STATUS%')) l2
ON l1.applicationid = l2.applicationid
WHERE l1.action = 'VIEWED'
AND l1.userid = '$user'
AND l1.date >= '$dateminus7'
AND l2.applicationid IS NULL
您在两个查询(主查询和子查询)中有两个“ action ='XXX'”,它们在Common中没有任何记录。 换句话说,如果您要通过“查看”操作查找某些应用程序。 您不需要使用查询:
从日志中选择applicationid userid ='$ user'AND date> ='$ dateminus7'AND(类似于“已提交注释%”的操作或类似于“已更改状态%”的操作)的日志
不知道我是否错过了什么,这是否有帮助。 我会遵循的。
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.