结合生成序列并计数到一个查询中

时间:2019-03-14 05:24:17

标签: postgresql subquery generate-series

Postgres版本9.4.18,PostGIS版本2.2。

我从这个问题中删除了一些有关表格的细节,因为我怀疑是否需要回答这个问题。如有必要,我可以重新添加这些详细信息。

所需结果: 我想要一年中的每个星期和一天中的小时的总数(0100至5223)。我能够成功生成一系列0100到5223(实际上是5300),并且能够分别获得一年中每个星期和一天中的每个小时的总数,但是我无法合并查询因此仍然显示一年零零几小时的星期几/小时。我想将计数结果与generate_series结合起来(最好将结果除以30)以得到如下结果。

MM-DD  | count_not_zero | count_not_zero_divided_by_30
-------+----------------+----------------------------
0100  |       10        |  33.3
0101  |       0         |  0
0102  |       0         |  0
...
0123  |       0         |  0
0200  |       3         |  10
0201  |       10        |  33.3
...
5223  |       20        |  66.6

以下是适用于我的单个查询,希望将它们组合在一起

SELECT DISTINCT f_woyhh(d::timestamp) as woyhh 
FROM generate_series(timestamp '2018-01-01', timestamp '2018-12-31', interval '1 hour') d 
GROUP BY woyhh
ORDER by woyhh asc;

SELECT dt, count(*) FROM 
(SELECT f_woyhh((time)::timestamp at time zone 'utc' at time zone 'america/chicago') 
AS dt, 
EXTRACT(YEAR FROM time) AS ctYear, count(*) 
AS ct 
FROM counties c 
INNER JOIN ltg_data d ON ST_contains(c.the_geom, d.ltg_geom) 
WHERE countyname = 'Milwaukee' AND state = 'WI' AND EXTRACT(YEAR from time) > '1987' GROUP BY dt, EXTRACT(YEAR from time)) 
AS count group by dt;

上面第二个查询的结果是(并且跳过了我不想要的零计数dt):

dt  | count
-------+-------
0100  |    10      
0104  |    5       
0108  |    4     

...

结论: 我正在尝试将上述工作中的单个查询合并为一个查询,该查询提供三三列的结果-哇,计数和计数除以30。我想包括县中零的哇,以便我有全套的东西。

感谢您的帮助!

1 个答案:

答案 0 :(得分:0)

我找到了答案。我明天将发布它,但是我想今天放它,这样就没有人不必要地解决这个问题。我很抱歉格式化。

WITH CTE_Dates AS (SELECT DISTINCT f_woyhh(d::timestamp) as dt 
FROM generate_series(timestamp '2018-01-01', timestamp '2018-12-31', interval '1 hour') d), 
CTE_WeeklyHourlyCounts AS (SELECT dt, count(*) as ct 
FROM (SELECT f_woyhh((time)::timestamp at time zone 'utc' at time zone 'america/chicago') as dt, 
EXTRACT(YEAR FROM time) as ctYear, count(*) as ct 
FROM counties c 
INNER JOIN ltg_data d on ST_contains(c.the_geom, d.ltg_geom) 
WHERE countyname = 'Milwaukee' AND state = 'WI' AND EXTRACT(YEAR from time) > '1987' 
GROUP BY dt,
EXTRACT(YEAR from time)) as count group by dt), 
CTE_FullSTats AS (SELECT CTE_Dates.dt as dt, CAST(CTE_WeeklyHourlyCounts.ct as decimal) as ct 
FROM CTE_Dates LEFT JOIN CTE_WeeklyHourlyCounts ON CTE_WeeklyHourlyCounts.dt = CTE_Dates.dt 
GROUP BY CTE_Dates.dt, CTE_WeeklyHourlyCounts.ct, CTE_WeeklyHourlyCounts.dt) SELECT dt, COALESCE(ct, 0) 
AS count, round(((COALESCE(ct,0) * 100) / 30),0) as percent FROM CTE_FullStats 
GROUP BY dt, ct ORDER BY dt;