具有多个左连接的查询导致查询锁定

时间:2012-06-19 07:18:56

标签: mysql

我正在尽可能地优化这个查询,但是由于这个查询,我仍然得到查询锁。任何人都可以提供一些改进它的建议。查询从表中获取最后一天的条目。 / p>

QUERY:

SELECT CR.id,
       CR.servicecode,
       CR.leadtime,
       CR.redirecturl,
       CRE.custemail,
       CRE.custlname,
       CRE.custfname,
       CRE.duration,
       CR.userid,
       AA.lpintrotimearr,
       AA.lpintrotimedep,
       AA.landdatetimearr,
       AA.landdatetimedep,
       CR.newcustid,
       cre.CRE.custmobilephone,
       CRE.brandname
FROM   response CR
       LEFT JOIN agreement AA
              ON CR.id = AA.id
       LEFT JOIN request CRE
              ON CRE.id = CR.id
WHERE  CR.id > '20120617145243'
       AND CR.approved = 1
       AND CR.chlapproved != 0
       AND CR.chlapproved IS NOT NULL
       AND AA.id IS NOT NULL
       AND ( AA.stdsign != 'on'
              OR AA.stdsign IS NULL )
       AND ( AA.ivaflag = 0
              OR AA.ivaflag IS NULL )
       AND ( AA.opt IS NULL
              OR AA.opt = 0 );

EXPLAIN:

Explain commands result

一种方法是索引所有3个(AA.stdsign,AA.ivaflag和AA.opts)列,但所有三个标志(AA.stdsign,AA.ivaflag和AA.opts)只能有3个不同的值。索引这些减少查询运行时间?

所有id都是varchar(60)数据类型。

1 个答案:

答案 0 :(得分:1)

查询本身没有太多改进。 另一方面,在AA.stdsignAA.ivaflagAA.opts上设置索引应该会有很大帮助。

正如您的EXPLAIN所示,您的AA表中找不到合适的密钥,并且必须扫描所有534956行以满足WHERE条款。

[编辑] 最后一个提示:对主键使用大型列(例如VARCHAR(60))可能是次优的。

第一个原因:每次你需要引用一行(例如在外键中)时,你需要另一个VARCHAR(60)

第二个原因:对字符串的比较比对整数的比较慢(因此它可能使JOIN慢于必要的速度)

您可能希望在表格中添加INT列,并将其用作主键。