执行以下查询需要时间。是否有任何重写可能性?
Query;
SELECT t_product.a_productid,
t_product.a_mpactive,
t_product.a_active,
trim( substring_index(a_reference, '_',-1)) as a_reference,
t_product.a_shopid,
t_productlang.a_name,
t_deactivatedproduct.a_reason
FROM t_deactivatedproduct
inner join ( SELECT max(a_deactivatedproductid) as a_deactivatedproductid
FROM t_deactivatedproduct
GROUP by t_deactivatedproduct.a_productid
) as a on a.a_deactivatedproductid = t_deactivatedproduct.a_deactivatedproductid
INNER JOIN t_product ON t_product.a_productid = t_deactivatedproduct.a_productid
INNER JOIN t_productlang ON t_product.a_productid = t_productlang.a_productid
AND t_product.a_shopid IN( 2, 3, 5, 6, 7, 10, 8, 15, 12, 16, 17, 26, 27, 28)
WHERE t_product.a_ispublished = 1
AND ( ( t_product.a_active = 1 AND t_product.a_mpactive = 0) OR (t_product.a_active = 0 AND t_product.a_mpactive = 1)
OR ( t_product.a_active = 0 AND t_product.a_mpactive = 0 ) )
ORDER BY t_deactivatedproduct.a_deactivatedproductid DESC
limit 700
有谁能告诉我哪里有问题,怎么改?
2条答案
按热度按时间vwkv1x7d1#
所有的表都使用索引,所以没有太多需要优化的地方。
我看到你试图使用一个派生表来找到每个productid的最大id。我会这样写:
这是一种在不使用子查询的情况下获取每组最大行的方法。比较
d1
和d2
两行。d2
必须具有相同的productid和更大的deactivatedproductid。如果没有这样的行,则外部联接将为其列返回NULL。因此,您可以知道d1
在该组中具有最大的ID。您的方法的问题是它为子查询的结果创建了一个临时表,这是非常昂贵的。我发现哪种方法更快取决于组的大小和不同组的数量,但是我上面展示的方法可能比您正在使用的派生表方法更快。另请参见我对检索每个组中的最后一条记录的回答- MySQL
fquxozlt2#
改进的索引:
(它们也处理Bill建议的更改。)
由于
ORs
,t_product上的索引可能没有用。如需进一步讨论,请提供
SHOW CREATE TABLE
和EXPLAIN SELECT ...