SQL查询根据时间范围对用户活动进行分组

时间:2017-01-20 08:37:50

标签: sql postgresql conditional-aggregation

我有一个包含两列的表,id和modifiedDate。我想查询此表以列出时间范围内每个id的活动。 我的表看起来像:

+-----+------------+
| ID  |     Date   |
+-----+------------+
| 1   | 2017.01.19 |
| 1   | 2017.01.18 |
| 1   | 2017.01.10 |
| 1   | 2017.01.09 |
| 2   | 2017.01.19 |
| 2   | 2017.01.18 |
| 2   | 2017.01.10 |
| 2   | 2017.01.09 |
+-----+------------+

Desired output: 

+-----+-----------------+------------+-------+
| ID  |     this week   | last week  | total |
+-----+-----------------+------------+-------+
| 1   |        2        |      2     |   4   | 
| 2   |        2        |      2     |   4   |
+-----+-----------------+------------+-------+

3 个答案:

答案 0 :(得分:0)

这就像Oracle SQL上的查询一样

 SELECT id, 
  COUNT(decode(to_char(t.modifydate,'iyyy-iw'),to_char(sysdate,'iyyy-iw'),1)) this_week, 
  COUNT(decode(to_char(t.modifydate,'iyyy-iw'),to_char(sysdate-7,'iyyy-iw'),1)) prev_week, 
  COUNT(id) total
FROM  test_tbl1 t
GROUP BY  id 

答案 1 :(得分:0)

这应该适用于MySQL

SELECT `id`, 
    COUNT(CASE WHEN WEEKOFYEAR(`date`) = WEEKOFYEAR(CURDATE()) THEN 1 END) this_week, 
    COUNT(CASE WHEN WEEKOFYEAR(`date`) = WEEKOFYEAR(CURDATE())-1 THEN 1 END) prev_week, 
    COUNT(id) total
FROM  `table`
GROUP BY `id`;

答案 2 :(得分:0)

你需要条件聚合,可以使用Postgres中的filter子句很好地完成(自9.4起)

select id, 
       count(*) filter (where this_week), 
       count(*) filter (where last_week),
       count(*) as total
from (
  select id, 
         date_trunc('week', "date")::date = date_trunc('week', current_date)::date as this_week,
         date_trunc('week', "date")::date = date_trunc('week', current_date)::date - 7 as last_week
  from data
) t
group by id
order by id;

或者,您可以使用to_char()将日期缩短为一周/年组合:

select id, 
       to_char("date", 'iyyy-iw') = to_char(current_date, 'iyyy-iw') as this_week,
       to_char("date", 'iyyy-iw') = to_char(current_date - 7, 'iyyy-iw') as last_week
from data