2016-04-28 12 views
0

私はこのようなのようなユーザの訪問のテーブルを持っている:条件付き集約行

SELECT * FROM visits ORDER BY start_time; 

user_id |  start_time  |  end_time 
---------+---------------------+--------------------- 
     10 | 2016-06-01 05:45:00 | 2016-06-01 06:00:00 
     10 | 2016-06-01 06:05:00 | 2016-06-01 06:30:00 
     10 | 2016-06-01 06:10:00 | 2016-06-01 06:40:00 
     10 | 2016-06-02 10:00:00 | 2016-06-01 10:30:00 
     10 | 2016-06-03 13:00:00 | 2016-06-01 14:00:00 

私は同様に、訪問が重複し、又は互いに10分以内である行を「マージ」する:

互いの
user_id |  start_time  |  end_time 
---------+---------------------+--------------------- 
     10 | 2016-06-01 05:45:00 | 2016-06-01 06:40:00 
     10 | 2016-06-02 10:00:00 | 2016-06-01 10:30:00 
     10 | 2016-06-03 13:00:00 | 2016-06-01 14:00:00 
  • 最初の3行は、最初の2行は、5分(10分未満)内にあるので、1にマージされ、第3段目は、最後の三つの行
  • 第二に重なります行がそれらの10分以内ではないので、sが

私は、これは複数の行に依存する行ごとに、グループ化関数の戻り値以来GROUP BYを使用して可能であるとは思いません変更されません。私はウィンドウの機能が助けになるかもしれないと思っていたが、クエリを構築するために苦労していた。

私はAWS赤方偏移

任意の助け

感謝を使用しています!

答えて

0

これにはウィンドウ/解析関数を使用できます。私はこのバージョンがあなたのデータに作用すると思う:

select user_id, min(start_time) as start_time, max(end_time) as end_time 
from (select t.*, 
      sum(case when start_time > prev_end_time + interval '10' minute 
         then 1 else 0 
       end) over (partition by user_id order by start_time) as grp 
     from (select t.*, 
        lag(end_time) over (partition by user_id order by start_time) as prev_end_time 
      from t 
      ) t 
    ) t 
group by grp, user_id; 

この方法はすべてのデータで機能するとは限りません。特に、ユーザーの開始時刻が重複していないことを前提としています。また、複雑な多重オーバーラップでもファンキーになることがあります。しかし、多くの状況で、このロジックは機能します。