按时间帧分组的行数

时间:2016-01-22 14:32:02

标签: sql postgresql

我有什么:

| id | timestamp  |
| ---| -----------|
| 1  | 1453212172 |
| 2  | 1453512172 |
| 3  | 1453712172 |
...

我想获得按时间帧分组的条目数。从2015-11-01 20:00开始,我需要一个持续3天的小组的计数:

| count | from       | to
| ------| -----------|-----------
| 34    | day 0, 8am | day 3, 8am
| 10    | day 3, 8am | day 6, 8am
| 56    | day 6, 8am | day 9, 8am
...

我发现的只是整天。有没有一种很好的方法在数据库层上做到这一点?我让它运行的唯一方法是使用多个查询并在应用程序层计算它,但它太昂贵了。

1 个答案:

答案 0 :(得分:1)

由于您将数据存储为时间戳,因此您可以通过简单的计算完成此操作,因为3天是:

24 x 60 * 60 = 86400

与获取数据集的最小和最大时间戳的存储过程结合使用,将它们转换为整数,然后使用WHILE循环迭代数据,直到它到达结尾,返回摘要行为你需要:

CREATE OR REPLACE FUNCTION get_counts() RETURNS TABLE(row_count integer, from_time integer, to_time integer)
AS $BODY$
  DECLARE 
    current_timestamp INTEGER;
    maximum_timestamp INTEGER;
    next_timestamp INTEGER;
  BEGIN
    current_timestamp := (SELECT CAST(EXTRACT(epoch FROM MIN(timestamp)) AS integer) FROM test);
    maximum_timestamp := (SELECT CAST(EXTRACT(epoch FROM MAX(timestamp)) AS integer) FROM test);

    WHILE current_timestamp < maximum_timestamp LOOP
      next_timestamp := current_timestamp + 86400;
      RETURN QUERY EXECUTE (SELECT COUNT(*) AS row_count, current_timestamp AS from_time, next_timestamp AS to_time FROM test WHERE CAST(EXTRACT(epoch FROM(timestamp)) AS integer) >= current_timestamp AND CAST(EXTRACT(epoch FROM(timestamp)) AS integer) < next_timestamp);
      current_timestamp := next_timestamp;
    END LOOP;
  END
$BODY$ LANGUAGE plpgsql;

该程序未经测试,可能无法开箱即用,但可以让您了解自己可以做些什么。然后,您可以从整数时间戳转换回应用程序端的真实时间戳。