如何创建有效的索引以快速检索最后一天的数据?

时间:2019-02-12 18:45:33

标签: postgresql indexing

我有一个表,其中包含118m行数据,目前还无法分区。我希望能够快速检索最近24小时的数据。格式为:

created_at | page_id
timestampz     text

这是最好的方法吗? (虽然出现有关IMMUTABLE的错误)

CREATE INDEX my_table_last_day
ON my_table (created_at)
WHERE date(created_at) = date(current_timestamp) - INTERVAL '1 day'

如果我每天获得约20万行新记录,是否可以有效地更新?

1 个答案:

答案 0 :(得分:1)

只需要在created_at::date上有一个索引。 where资格不是必需的,并且随着current_timestamp的变化会做一些奇怪的事情。 default Postgres B-tree index可以处理相等性和范围查询。

请务必使用多余的括号。

test=> create index my_table_created_at_date on my_table((created_at::date));
CREATE INDEX

test=> analyze my_table;                                                    
ANALYZE

test=> explain select * from my_table WHERE date(created_at) = date(current_timestamp) - INTERVAL '1 day';
                                       QUERY PLAN                                        
-----------------------------------------------------------------------------------------
 Index Scan using my_table_created_at_date on my_table  (cost=0.29..8.43 rows=2 width=8)
   Index Cond: (date(created_at) = (date(CURRENT_TIMESTAMP) - '1 day'::interval))

还要确保仅在created_at上建立索引,以涵盖其他非日期查询。

test=> create index my_table_created_at on my_table(created_at);
CREATE INDEX

test=> analyze my_table ;
ANALYZE

test=> explain select * from my_table WHERE created_at between (current_timestamp - INTERVAL '1 day') and current_timestamp;
                                                  QUERY PLAN                                                   
---------------------------------------------------------------------------------------------------------------
 Index Only Scan using my_table_created_at on my_table  (cost=0.29..4.39 rows=5 width=8)
   Index Cond: ((created_at >= (CURRENT_TIMESTAMP - '1 day'::interval)) AND (created_at <= CURRENT_TIMESTAMP))