【问题标题】:Postgres - Using window function in grouped rowsPostgres - 在分组行中使用窗口函数
【发布时间】:2020-11-27 19:02:57
【问题描述】:

根据https://www.postgresql.org/docs/9.4/queries-table-expressions.html#QUERIES-WINDOW 的 Postgres Doc 声明

如果查询包含任何窗口函数 (...),则在执行任何分组、聚合和 HAVING 过滤后评估这些函数。也就是说,如果查询使用任何聚合、GROUP BY 或 HAVING,则窗口函数看到的行是组行,而不是来自 FROM/WHERE 的原始表行。

我没有得到“然后窗口函数看到的行是组行而不是来自 FROM/WHERE 的原始表行”的概念。请允许我用一个例子来解释我的疑问:

使用下面这个准备运行的示例

with cte as ( 
  select 1 as primary_id, 1 as foreign_id, 10 as begins
  union
  select 2 as primary_id, 1 as foreign_id, 20 as begins
  union
  select 3 as primary_id, 1 as foreign_id, 30 as begins
  union
  select 4 as primary_id, 2 as foreign_id, 40 as begins
)
select foreign_id, count(*) over () as window_rows_count, count(*) as grouped_rows_count
from cte
group by foreign_id  

你可能会注意到结果是

因此,如果“窗口函数看到的行是组行”.. 那么 ¿为什么 window_rows_count 返回的值与 grouped_rows_count 不同?

【问题讨论】:

    标签: postgresql group-by window-functions


    【解决方案1】:

    如果您从查询中删除窗口函数:

    select foreign_id, count(*) as grouped_rows_count
    from cte
    group by foreign_id
    

    结果,果然是这样的:

    > foreign_id | grouped_rows_count
    > ---------: | -----------------:
    >          1 |                  3
    >          2 |                  1
    

    对于这个结果,也就是 2 行,如果你还应用了窗口函数 count(*) over(),它将返回 2,因为它计算了结果集的所有行,因为 over 子句为空,没有任何 @ 987654325@.

    【讨论】:

      【解决方案2】:

      您应该关注您帖子的最后一条评论。 为了进行更多分析,您可以处理以下查询:

      with cte as ( 
      
      
      select 1 as primary_id, 1 as foreign_id, 10 as begins
        union
        select 2 as primary_id, 1 as foreign_id, 20 as begins
        union
        select 3 as primary_id, 1 as foreign_id, 30 as begins
        union
        select 4 as primary_id, 2 as foreign_id, 40 as begins
      )
      select foreign_id, count(*) over (PARTITION BY foreign_id) as window_rows_count, count(*) as grouped_rows_count
      from cte
      group by foreign_id ;
      

      这次您会看到每个外国 id 获得 1 行。 在这个 url 上查看关于 postgres 的文档: https://www.postgresql.org/docs/13/tutorial-window.html

      窗口函数应用于前一次查询得到的整个集合。

      【讨论】:

        猜你喜欢
        • 2012-02-09
        • 1970-01-01
        • 2021-10-02
        • 1970-01-01
        • 1970-01-01
        • 1970-01-01
        • 2013-04-16
        • 1970-01-01
        • 1970-01-01
        相关资源
        最近更新 更多