与 group by 相比,在 sql 中使用 Over Partition

Using Over Partition in sql compared with group by

鉴于下面的 table 创建代码,是否有其他方法可以显示与

相同的结果
select b.*, count(*) over (partition by colour) bricks_total 
from bricks b;

使用 group bycount(*)?在这种情况下有什么区别?

create table bricks 
(
     brick_id integer,
     colour   varchar2(10),
     shape    varchar2(10),
     weight   integer
);

insert into bricks values (1, 'blue', 'cube', 1);
insert into bricks values (2, 'blue', 'pyramid', 2);
insert into bricks values (3, 'red', 'cube', 1);
insert into bricks values (4, 'red', 'cube', 2);
insert into bricks values (5, 'red', 'pyramid', 3);
insert into bricks values (6, 'green', 'pyramid', 1);

commit;

此查询将每种颜色的总数放在每行中:

select b.*, count(*) over (partition by colour) as bricks_total
from bricks b;

在window函数之前,典型的解决方案是相关子查询:

select b.*,
       (select count(*) from bricks b2 where b2.colour = b.colour) as bricks_total
from bricks b;

您也可以使用 join 和聚合来表示:

select b.*, bb.bricks_total
from bricks b join
     (select bb.colour, count(*) as bricks_total
      from bricks bb
      group by bb.colour
     ) bb
     using (colour);

这些并非 100% 相同。不同之处在于,即使值为 NULL,原始代码也会 return 计数 colour。此代码 returns 0.

因此,更精确的等价物是:

select b.*,
       (select count(*)
        from bricks b2
        where b2.colour = b.colour or
              b2.colour is null and b.colour is null
       ) as bricks_total
from bricks b;