Mysql需要很长时间才能达到更大的限制

标签 mysql sql

我们有几个 MySql 查询,当选择较少数量的记录时(即限制为 0,100),它们表现良好。

当我们将限制从 100 增加到 1000(即限制 0,1000)时,查询花费的时间几乎增加了 10 倍到 50 倍。

已编辑 我们如何优化它?解释计划在下面给出,

Explain PLan

查询

 Select  
   concat(floor(TIMESTAMPDIFF(MINUTE,x.msgCreatedOn, NOW())/60),':',floor(TIMESTAMPDIFF(MINUTE,x.msgCreatedOn, NOW())%60)) as aging,
   x.`actionStartDate`,  
   concat(floor(TIMESTAMPDIFF(MINUTE,x.`actionStartDate`, NOW())/60),':',floor(TIMESTAMPDIFF(MINUTE,x.`actionStartDate`, NOW())%60)) as workflowAging 
from 
   (  
    Select 
        * 
    from  
        t_wk_dtls d left 
    join  t_s_dtls s  on  (d.id = s.`work_parentId` or d.`parentId` = s.`work_parentId`) and d.`currentlyActive` = true  
    left join t_w b on b.basketId=d.toBasketId  
    left join t_u u on d.toUserId= u.userId 
    left join t_s_m sch on d.sourceId=sch.schMsgId   
    left join t_l_s_a a on a.orgId='1002'  
            AND ((((a.`type`='TWITTER' and d.channel in (1,34)) 
or (a.`type`='FACEBOOK' and d.channel in (6,7)) 
or (a.`type`='GOOGLEPLUS' and d.channel in (5,25)) 
or (a.`type`='LINKEDIN' and d.channel =30) 
or (a.`type`='GOOGLEPLUS' and d.channel=36) 
or ((a.`type`='YOUTUBE' or a.`type`='GOOGLEPLUS') and d.channel=27) 
or (a.`type`='TUMBLR' and d.channel in (29,31)) 
or (a.`type`='INSTAGRAM' and d.channel=35) ) AND d.userChannelId=a.socialId)              OR (a.`type`='BLOG' and d.channel in (9,11,15,21) AND d.msgId=a.socialId)) 
     left join t_l l on l.leadId=a.leadId and l.orgId='1002' 
where 
     d.currentlyActive = true 
 and d.dataSource ='SOLR'   
 and d.profileId = '148' AND msgCreatedOn BETWEEN '2016-03-14 18:30:00' AND '2016-03-31 18:29:59'  
 order by d.msgCreatedOn desc limit 0,100000 ) as x

最佳答案

你真的需要一个子查询吗?现在,请注意解释结果中的“依赖子查询”——它通常意味着子查询对每个返回的外部行执行一次(参见 point 18.2.1.18.2 in "18.2.1.18 Subquery optimization" )。因此,随着返回的行越来越多,您的执行时间呈指数级增长。

因为您只是在子查询中执行 select * from,这样的事情不会完成同样的事情吗?

Select 
   concat(floor(TIMESTAMPDIFF(MINUTE,x.msgCreatedOn, NOW())/60),':',floor(TIMESTAMPDIFF(MINUTE,x.msgCreatedOn, NOW())%60)) as aging,
   x.`actionStartDate`,  
   concat(floor(TIMESTAMPDIFF(MINUTE,x.`actionStartDate`, NOW())/60),':',floor(TIMESTAMPDIFF(MINUTE,x.`actionStartDate`, NOW())%60)) as workflowAging 
from  
    t_wk_dtls d left 
join  t_s_dtls s  on  (d.id = s.`work_parentId` or d.`parentId` = s.`work_parentId`) and d.`currentlyActive` = true  
left join t_w b on b.basketId=d.toBasketId  
left join t_u u on d.toUserId= u.userId 
left join t_s_m sch on d.sourceId=sch.schMsgId   
left join t_l_s_a a on a.orgId='1002'  
        AND ((((a.`type`='TWITTER' and d.channel in (1,34)) 
or (a.`type`='FACEBOOK' and d.channel in (6,7)) 
or (a.`type`='GOOGLEPLUS' and d.channel in (5,25)) 
or (a.`type`='LINKEDIN' and d.channel =30) 
or (a.`type`='GOOGLEPLUS' and d.channel=36) 
or ((a.`type`='YOUTUBE' or a.`type`='GOOGLEPLUS') and d.channel=27) 
or (a.`type`='TUMBLR' and d.channel in (29,31)) 
or (a.`type`='INSTAGRAM' and d.channel=35) ) AND d.userChannelId=a.socialId)     OR (a.`type`='BLOG' and d.channel in (9,11,15,21) AND d.msgId=a.socialId)) 
 left join t_l l on l.leadId=a.leadId and l.orgId='1002' 
where 
 d.currentlyActive = true 
 and d.dataSource ='SOLR'   
 and d.profileId = '148' AND msgCreatedOn BETWEEN '2016-03-14 18:30:00' AND     '2016-03-31 18:29:59'  
 order by d.msgCreatedOn desc limit 0,100000;

(除了开头的列列表中的表前缀由“x”改为真实的)

关于Mysql需要很长时间才能达到更大的限制,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/36352295/

相关文章:

java - 从 context.xml 文件获取数据库凭据

mysql - 合并一个日期时间的日期和另一个日期时间的时间

mysql - 将第二个 MySQL 表中的数据添加到第一个表的结果中

php - 带条件查询的查询

php - PHP/MySQL-mysql_result()期望参数1为资源, boolean 值在[duplicate]中给出

MySQL 按 2 个表的 2 列对表进行排序

c# - 将sql返回保存在一个字符串中

sql - 无法通过 grails 应用程序插入 MSSQL

mysql - 跨多个联接表的 SQL 查询

mysql - 每周统计的sql查询错误