结合CTE的结果

时间:2015-02-04 12:42:38

标签: postgresql count common-table-expression

我有几个CTE。 CTE1A计算区域1中A类商店的数量.CTE1B计算区域1中B类商店的数量,直至CTE1D。类似地,CTE2B计算区域2中B类商店的数量,依此类推。 shop_types CTE选择所有类型的商店:A,B,C,D。如何显示一个表格,显示每个区域(列)每种类型的商店数量(行)。 例如:

    1    2    3    4    5
A   0    7    4    0    0
B   2    3    8    2    9
C   8    5    8    1    6
D   7    1    5    4    3

数据库有2个表:

表区域:shop_id,region_id

表店:shop_id,shop_type

WITH 
shop_types AS (SELECT DISTINCT shops.shop_type AS type FROM shops WHERE shops.shop_type!='-9999' AND shops.shop_type!='Other'),
cte1A AS (
SELECT regions.region_id, COUNT(regions.shop_id) AS shops_number, shops.shop_type
FROM regions
RIGHT JOIN shops
ON shops.shop_id=regions.shop_id
WHERE regions.region_id=1
AND shops.shop_type='A'
GROUP BY shops.shop_type,regions.region_id)
SELECT * FROM cte1A

1 个答案:

答案 0 :(得分:1)

我不完全确定我理解你为什么会这么做,但似乎你在寻找这样的事情:

select sh.shop_type, 
       count(case when r.region_id = 1 then 1 end) as region_1_count,
       count(case when r.region_id = 2 then 1 end) as region_2_count,
       count(case when r.region_id = 3 then 1 end) as region_3_count
from shops sh
  left join regions r on r.shop_id = sh.shop_id
group by sh.shop_type
order by sh.shop_type;

您需要为输出中要包含的每个区域添加一个case语句。

如果您使用的是Postgres 9.4,您可以使用filter条件替换案例陈述,这样可以使意图更容易理解(我认为)

count(*) filter (where r.region_id = 1) as region_1_count,
count(*) filter (where r.region_id = 2) as region_2_count, 
...

SQLFiddle:http://sqlfiddle.com/#!1/98391/1


在你问之前:不,你不能使列数和动态"基于select语句。在实际执行语句之前,必须定义查询的列列表。