代码之家  ›  专栏  ›  技术社区  ›  Zack Xu

如何在Postgres中从时间戳中自动提取或索引日期?

  •  0
  • Zack Xu  · 技术社区  · 7 年前

    我们有一个带有时间戳字段的Postgres表 created_at . 定期,我们需要找到所有记录的日期字段 创建于 一定数量的。

    select * from table where extract(day from created_at) = 3;
    

    我怀疑这效率不高。如果是的话,我可以创建一个索引来提高上面的效率吗?

    如果不可能,我们可以创建一个单独的列,名为 created_at_day 并在其上创建索引。

    select * from table where created_at_day = 3;
    

    比如说 创建于 可以更新。每当这种情况发生, 也应该更新。

    创建日期 创建于 ? 如果是,怎么做?

    创建于 创建日期 列。但我只是想知道是否有一个更简单,自动化的方法来做到这一点。

    1 回复  |  直到 7 年前
        1
  •  2
  •   Kaushik Nayak    7 年前

    可以在上创建索引 extract(day from created_at)

    要看到区别:

    创建表

    knayak=# create table t as select i ,now()::timestamp + interval '1 days' * i as created_at from generate_series(1,10000) as i;
    SELECT 10000
    

    knayak=# create index ind_created_at on t(created_at);
    CREATE INDEX
    
    knayak=# explain analyze select * from t where extract(day from created_at) = 3;
                                               QUERY PLAN
    -------------------------------------------------------------------------------------------------
     Seq Scan on t  (cost=0.00..205.00 rows=50 width=12) (actual time=1.049..6.020 rows=328 loops=1)
       Filter: (date_part('day'::text, created_at) = '3'::double precision)
       Rows Removed by Filter: 9672
     Planning time: 0.392 ms
     Execution time: 6.070 ms
    (5 rows)
    

    使用提取创建索引

    knayak=# drop index ind_created_at;
    DROP INDEX
    knayak=# create index ind_created_at on t( extract(day from created_at) );
    CREATE INDEX
    knayak=# explain analyze select * from t where extract(day from created_at) = 3;
                                                            QUERY PLAN
    --------------------------------------------------------------------------------------------------------------------------
     Bitmap Heap Scan on t  (cost=4.67..61.66 rows=50 width=12) (actual time=0.110..0.260 rows=328 loops=1)
       Recheck Cond: (date_part('day'::text, created_at) = '3'::double precision)
       Heap Blocks: exact=54
       ->  Bitmap Index Scan on ind_created_at  (cost=0.00..4.66 rows=50 width=0) (actual time=0.093..0.093 rows=328 loops=1)
             Index Cond: (date_part('day'::text, created_at) = '3'::double precision)
     Planning time: 0.316 ms
     Execution time: 0.314 ms
    (7 rows)