2017-11-01 3 views
1

私はユーザーイベントを持つテーブルと、システム内のすべてのイベントの名前を持つテーブルを持っています。私は必要なもの0件のカウントを含め、イベントごとにユーザーあたりのイベント数を計算する

は、バージョンが不明ANSI SQL彼らは0

方言を持っていたのイベントをされるなど、各ユーザーごとのイベントカウント、です。データベースはPresto 0.186です。ここで

は例です:

with 
event_names (name) as (values 
    ('event_1'), ('event_2'), ('event_3'), ('event_4') 
) 
, events (user_id, event_name, occurred_at) as (values 
    ('id1', 'event_1', timestamp '2017-10-10 00:01:00') 
    , ('id1', 'event_2', timestamp '2017-10-10 00:02:00') 
    , ('id1', 'event_2', timestamp '2017-10-10 00:03:00') 
    , ('id2', 'event_2', timestamp '2017-10-11 00:01:00') 
    , ('id2', 'event_3', timestamp '2017-10-11 00:02:00') 
    , ('id2', 'event_3', timestamp '2017-10-11 00:03:00') 
    , ('id2', 'event_4', timestamp '2017-10-11 00:03:00') 
    , ('id3', 'event_1', timestamp '2017-10-12 00:03:00') 
    , ('id3', 'event_4', timestamp '2017-10-12 00:04:00') 
) 

select user_id, event_name, count(*) as event_count, sum(count(*)) over (partition by user_id) as total_events 
from events 
group by 1, 2 
order by 1, 2; 

このクエリは、自然に私のユーザーが送信しなかったイベントのためにのみカウントを与える:私は必要なもの

user_id | event_name | event_count 
---------+------------+------------- 
id1  | event_1 |   1 
id1  | event_2 |   2 

id2  | event_2 |   1 
id2  | event_3 |   2 
id2  | event_4 |   1 

id3  | event_1 |   1 
id3  | event_4 |   1 

は以下の通りです:

user_id  | name | event_count 
-------------+---------+------------- 
id1   | event_1 |   1 
id1   | event_2 |   2 
id1   | event_3 |   0 
id1   | event_4 |   0 

id2   | event_1 |   0 
id2   | event_2 |   1 
id2   | event_3 |   2 
id2   | event_4 |   0 

id3   | event_1 |   1 
id3   | event_2 |   0 
id3   | event_3 |   0 
id3   | event_4 |   1 

答えて

2

cross joinを使用してすべての行を生成します。

select u.user_id, en.event_name, count(e.user_id) as event_count, 
     sum(count(e.user_id)) over (partition by user_id) as total_events 
from (select distinct user_id from events) u cross join 
    (select distinct event_name from events) en left join 
    events e 
    on e.user_id = u.user_id and e.event_name = en.event_name 
group by 1, 2 
order by 1, 2; 

を使用すると、ユーザーやイベントのリストを持つ他のテーブルを持っている場合は、あなたの代わりにサブクエリのそれらを使用することができます。そして、存在するデータに持ち込みます。

関連する問題