在两列上创建索引以检查日期是不是介于这两个列之间
Posted
技术标签:
【中文标题】在两列上创建索引以检查日期是不是介于这两个列之间【英文标题】:Creating indexes on two columns to check if a date falls between those two在两列上创建索引以检查日期是否介于这两个列之间 【发布时间】:2016-09-03 20:04:13 【问题描述】:我正在使用 Laravel 5 和 postgres。有一个表有两列'start_date'和'end_date'。我想创建一个索引,以便我可以轻松检查日期是否介于这两者之间。
我正在使用以下代码来做到这一点
$table->date ( 'start_date' );
$table->index('start_date');
$table->date ( 'end_date' );
$table->index('end_date');
但我看到也有创建复合索引的选项。
我的问题是为上述场景创建索引的最佳方法是什么?
【问题讨论】:
取决于数据分布以及您是否总是要指定两列的事实。如果没有,最好单独索引它们。如果您始终将两列都放在哪里,那么两列索引会比每列两列更快。 【参考方案1】:取决于您的查询是什么。而其他数据库(如 mysql)在大多数情况下每个表只能使用一个索引,但 postgresql 可以使用多个索引。
因此,如果您在 start_date 和 end_date 上有两个单独的索引,那么如果 where close 对两列都有条件,则它们都将被使用。请注意,不能保证两个索引甚至其中一个都可以使用。例如,如果您只有几行,那么直接检索数据而不参考索引会快得多。在这种情况下,复合索引也没有多大用处。
如果您有其他查询只涉及两列中的一列,那么最好使用两个单独的索引
【讨论】:
【参考方案2】:要回答您的具体问题 - 查找开始/结束范围之间的日期,您想要的是(日期)范围类型的索引。
您可以在表定义中使用实际的daterange
,但这不是必需的,因为 PostgreSQL 支持索引中的表达式。
CREATE TABLE t1 (start_date date, end_date date);
INSERT INTO t1 SELECT '2001-01-01' + i, '2001-02-01' + i FROM generate_series(0,9999) i;
CREATE INDEX date_range_idx ON t1 USING gist (daterange( start_date, end_date) );
SELECT * FROM t1 WHERE daterange(start_date,end_date) @> '2002-01-01'::date;
详情请参阅manual。
【讨论】:
感谢您的回答,内容丰富。但我现在只想使用 Laravel 迁移 API。以上是关于在两列上创建索引以检查日期是不是介于这两个列之间的主要内容,如果未能解决你的问题,请参考以下文章
非聚集索引 - 几乎相同需求的一个或两个索引(两个表之间的连接)?
什么是 django 查询来查找搜索日期在两列之间的记录不是?