使用 `COUNT` 优化 SQL 查询

Optimize SQL query using `COUNT`

我有下面的 SQL 查询(我正在使用 MariaDB/MySQL),它工作正常。但我想知道我是否可以 simplify/optimize 它。我面临的困难是因为 COUNTINNER JOIN。我真的需要子查询 IN 还是您认为我有办法消除它?

SELECT a.* 
FROM aaa a 
INNER JOIN bbb b ON a.field1 = b.field1 
WHERE a.yyy = 'yyy' AND b.zzz = 'zzz' 
AND a.field1 IN (
    SELECT field1 
    FROM bbb 
    WHERE xxx = 'x' 
    GROUP BY field1 
    HAVING COUNT(field1) <= 5
)

谢谢!

您的查询可能会尽可能好,但您也可以尝试加入子查询而不是使用 IN

SELECT DISTINCT a.*
FROM aaa AS a
INNER JOIN bbb b ON a.field1 = b.field1 
INNER JOIN (
    SELECT field1 
    FROM bbb 
    WHERE xxx = 'x' 
    GROUP BY field1 
    HAVING COUNT(*) <= 5
) AS bc ON a.field1 = bc.field1
WHERE a.yyy = 'yyy' AND b.zzz = 'zzz' 

我喜欢 Barmar 的回答,但由于 b 上的过滤,我建议进行小的(?)更改。 (我重新排列表格主要是为了遵循优化器可能的顺序。)

SELECT DISTINCT a.*
FROM  (
    SELECT field1 
    FROM bbb 
    WHERE xxx = 'x' 
    GROUP BY field1 
    HAVING COUNT(*) <= 5
) AS bc
INNER JOIN bbb AS b ON b.field1 = bc.field1 
INNER JOIN aaa AS a ON a.field1 = bc.field1
WHERE b.zzz = 'zzz' 
  AND a.yyy = 'yyy'

加上这些索引:

    bbb:  INDEX(xxx, field1)  -- this order
    b:    INDEX(field1, zzz)  -- either order
    a:    INDEX(field1, yyy)  -- either order

前两个复合索引将被“覆盖”。

Barmar 回答的主要变化是将 a.* 留在最后。

如果您想进一步讨论这个问题,提供 SHOW CREATE TABLEEXPLAIN 可能会有用。