首页 > 解决方案 > 无需进行两次查询即可限制 COUNT 聚合窗口函数的方法

问题描述

我们经常使用 COUNT 聚合窗口函数来返回查询将匹配的总行数,以便为最终用户提供轻松的分页。例子:

SELECT *, COUNT(*) OVER () total
FROM table
WHERE <condition>
LIMIT 20
OFFSET 0;

这对于我们的大多数表都非常有效,实际上总数不会超过几百行,因此对性能的影响可以忽略不计。

我们想做的是LIMIT计数到 10,000 并在达到 10,000 时停止计数。这是因为一些资源可能会无限增长,并且总数可能是 1M+ 行,这对于计算来说是非常昂贵的。

一种天真的方法是发出两次查询,应用限制为 10,000 并计算这些结果:

SELECT COUNT(*)
FROM (
  SELECT *
  FROM table
  WHERE <condition>
  LIMIT 10000
  OFFSET 0
) q;

我已经尝试过窗框并做类似的事情

ROWS BETWEEN 1 FOLLOWING AND 10000 FOLLOWING

这实际上返回了正确的东西,然而,EXPLAIN ANALYZE证明它比获得最终计数更昂贵的执行时间(当10000数字较小时它会更少)!

谁能想到一种方法(在单个查询中)使total最大值达到 10k 并有效地停止有效计数?

谢谢!

标签: sqlcountwindowaggregate-functions

解决方案


推荐阅读