在chipChange表中,我有数百万条记录。我想要学习的是优化下面的查询的方法。目前它看起来需要花费数小时才能
您认为我如何提高此类查询的效果?
UPDATE playerStats pst
INNER JOIN
(
Select
chipChange.uid,
sum(case when (type=2) and (eventId!=16 and eventId!=17 and eventId!=18 and eventId!=10) then 1 else 0 end) sum1,
sum(case when (type=1 or type=3 or type=9) and (eventId!=16 and eventId!=17 and eventId!=18 and eventId!=10) then 1 else 0 end) sum2,
sum(case when type=2 and eventId=10 then 1 else 0 end) sum3,
sum(case when (type=1 or type=3 or type=9) and eventId=10 then 1 else 0 end) sum4,
sum(case when type=2 and (eventId=16 or eventId=17 or eventId=18) then 1 else 0 end) sum5,
sum(case when (type=1 or type=3 or type=9) and (eventId=16 or eventId=17 or eventId=18) then 1 else 0 end) sum5
from chipChange
where (type=1 or type=2 or type=3 or type=9)
group by uid
) cht on pst.uid=cht.uid
SET
pst.total1 = cht.sum1 + cht.sum2,
pst.total2 = cht.sum1,
pst.total3 = cht.sum3 + cht.sum4,
pst.total4 = cht.sum3,
pst.total5 = cht.sum5 + cht.6,
pst.total6 = cht.sum5;
答案 0 :(得分:0)
此查询可以在您的数据库中创建锁定,甚至可以阻塞数据库服务器。
更好的选项将是一个存储过程,其中首先获取select查询中的所有值计算值并将它们保存在游标中,然后通过游标逐个更新目标表。
答案 1 :(得分:0)
我认为查询根本不会使用索引。
使用单独的子查询(取决于你的chipChange表所具有的索引)可能是值得的,每个查询可以使用索引来获取计数,然后只需将这些单独的查询LEFT OUTER加入到playerStats中。
这样的事情: -
UPDATE playerStats pst
LEFT OUTER JOIN
(
SELECT uid, COUNT(*) AS sum1 FROM chipChange WHERE type=2 and eventId NOT IN (16, 17, 18, 10) GROUP BY uid
) sub1 ON sub1.uid = pst.uid
LEFT OUTER JOIN
(
SELECT uid, COUNT(*) AS sum2 FROM chipChange WHERE type IN (1, 3, 9) and eventId NOT IN (16, 17, 18, 10) GROUP BY uid
) sub2 ON sub2.uid = pst.uid
LEFT OUTER JOIN
(
SELECT uid, COUNT(*) AS sum3 FROM chipChange WHERE type = 2 and eventId = 10 GROUP BY uid
) sub3 ON sub3.uid = pst.uid
LEFT OUTER JOIN
(
SELECT uid, COUNT(*) AS sum4 FROM chipChange WHERE type IN (1, 3, 9) and eventId = 10 GROUP BY uid
) sub4 ON sub4.uid = pst.uid
LEFT OUTER JOIN
(
SELECT uid, COUNT(*) AS sum5 FROM chipChange WHERE type = 2 and eventId IN (16, 17, 18) GROUP BY uid
) sub5 ON sub5.uid = pst.uid
LEFT OUTER JOIN
(
SELECT uid, COUNT(*) AS sum6 FROM chipChange WHERE type IN (1, 3, 9) and eventId IN (16, 17, 18) GROUP BY uid
) sub6 ON sub6.uid = pst.uid
SET
pst.total1 = COALESCE(sub1.sum1, 0) + COALESCE(sub2.sum2, 0),
pst.total2 = COALESCE(sub1.sum1, 0),
pst.total3 = COALESCE(sub3.sum3, 0) + COALESCE(cht.sum4, 0),
pst.total4 = COALESCE(sub3.sum3, 0),
pst.total5 = COALESCE(sub5.sum5, 0) + COALESCE(sub6.sum6, 0),
pst.total6 = COALESCE(sub5.sum5, 0);