我不确定这是否正是您正在寻找的,但也许它可以作为适应的基础。尽管我不使用纪元时间,但我经常需要在一段时间内生成汇总数据,因此可能有比我想出的更好的方法来操纵这些值。
创建和填充测试表
create table epoch_t(etime numeric);
insert into epoch_t
select extract(epoch from generate_series(now(),now() - interval '6 hours',interval '-10 minutes'));
要将时间划分为时段:
select generate_series(to_char(now(),'yyyy-mm-dd hh24:00:00')::timestamptz,
to_char(now(),'yyyy-mm-dd hh24:00:00')::timestamptz - interval '4 hours',
interval '-1 hour');
将纪元时间转换为 postgres 时间戳:
select timestamptz 'epoch' + etime * '1 second'::interval from epoch_t;
然后截断为小时:
select to_char(timestamptz 'epoch' + etime * '1 second'::interval,
'yyyy-mm-dd hh24:00:00')::timestamptz from epoch_t
按小时提供摘要信息:
select to_char(timestamptz 'epoch' + etime * '1 second'::interval,
'yyyy-mm-dd hh24:00:00')::timestamptz,
count(*)
from epoch_t
group by 1
order by 1 desc;
如果您可能在数据中存在差距,但需要报告零结果,请使用 generate_series 创建周期存储桶并将连接左连接到数据表。在这种情况下,我在上面的数据填充之前创建示例小时存储桶 - 9 小时而不是 6 小时,并加入将纪元时间转换为截断为小时的时间戳。
select per.sample_hour,
sum(case etime is null when true then 0 else 1 end) as etcount
from (select generate_series(to_char(now(),
'yyyy-mm-dd hh24:00:00')::timestamptz,
to_char(now(),'yyyy-mm-dd hh24:00:00')::timestamptz - interval '9 hours',
interval '-1 hour') as sample_hour) as per
left join epoch_t on to_char(timestamptz 'epoch' + etime * '1 second'::interval,
'yyyy-mm-dd hh24:00:00')::timestamptz = per.sample_hour
group by per.sample_hour
order by per.sample_hour desc;