这个查询引用了大约3百万条记录,现在需要一个绝对时间来运行。这些数据来自excel电子表格,其中cust/invoices列为下一行,2016年至2016年的月度值列为当前值。
此查询检查同一个月是否有相同/不同产品的值,如果可以忽略该值,则输出1;如果在后续查询中应考虑该值,则输出0。
我已经为product设置了一个索引,它负责初始条件,但子查询绝对会扼杀这一点:
UPDATE tbl_transactions a
SET ProdInCust_Mnth_Same_SameProd_LowerVal =
CASE WHEN
(
SELECT COUNT(TransactionID)
FROM tbl_transactions_tmp b
WHERE
b.TransactionID<>a.TransactionID AND
b.CustomerRef=a.CustomerRef AND
b.TransMonth=a.TransMonth AND
(
(
(b.Product='PLATINUM') AND
b.TransValue<0
)
OR
(
a.TransValue=0 AND
(b.Product='PLATINUM' OR b.Product='GOLD' OR b.Product='SILVER') AND
b.TransValue<0
)
OR
(
a.TransValue<0 AND
(b.Product='PLATINUM' OR b.Product='GOLD') AND
((b.TransValue=a.TransValue AND b.RowReference>a.RowReference) OR
b.TransValue<a.TransValue
)
)
)
)>0 THEN 1 ELSE 0 END
WHERE Product='GOLD';
解释产品:
id select_type table partitions type possible_keys key key_len ref rows filtered Extra
1 UPDATE a \N index IDX_tbl_transactions_Product PRIMARY 8 \N 2828152 100 Using where
2 DEPENDENT SUBQUERY b \N ref IX_Transactions_SP_ProcessTransAA IX_Transactions_SP_ProcessTransAA 45 finance.a.CustomerRef,finance.a.TransMonth 1 20.7 Using where; Using index
从视觉上看,它说这是一个完整的索引扫描,我认为红色背景表明这是坏的。
有什么想法我可以进一步优化这个。
3条答案
按热度按时间ahy6op9u1#
你可以尝试下面的方法-使用cte或temp表格,并使用case和where来评估预期的结果。在更新put时使用此表值。希望这可以帮助您创建查询。查询可能不会给出准确的结果,但可以帮助您创建查询。
vs91vp4v2#
你们有这个综合指数吗?或者从这两列开始的更宽的索引?
上个月是否可以每月计算一次信息或部分信息?将其存储在摘要表中,然后查询该表可能是一种更快的方法。
您是否知道自己是否受i/o限制?如果您是i/o绑定的,那么
innodb_buffer_pool_size
,您有多少ram,表有多大(gb)?cetgtptt3#
尝试将子查询的where子句中使用的所有字段的索引添加到表和use中
EXISTS
而不是COUNT
:参考:存在是否比计数(*)>0更有效?