0

假设我有一个包含int[]列和值的表:

'[1,4,1300]'::int4[]

我希望能够查询该列并获取true是否有任何元素与BETWEEN语句匹配。因此,在这种情况下,类似于:

SELECT id FROM table WHERE col && '[1000,2000]'::int4range或类似的。

该列使用gist__int_ops

4

3 回答 3

1

您可以将范围与包含运算符一起使用,例如:

select id 
from my_table 
where '[2,4]'::int4range @> any(col)

不幸的是,查询不使用索引。我认为您找不到可以执行此操作的查询(无需定义自己的运算符)。

更新。您可以尝试将范围转换为数组。

create or replace function int_range_to_array(int4range)
returns int[] language sql immutable as $$
    select array(
        select i 
        from generate_series(lower($1), upper($1)- 1) i)
$$;

select id
from my_table 
where col && int_range_to_array('[2,4]');

显然,性能取决于范围大小。

于 2019-10-19T20:59:28.793 回答
1

教条的答案是您不应该在表中使用数组,而应该使用子表。我通常不坚持教条,但在这种情况下,我认为这可能也是务实的答案。我在可扩展性 API 中没有看到任何看起来您甚至可以实现自己的扩展来执行此操作的索引。

如果您使用子表,您将返回使用BETWEEN..AND查询,而不是 int4range,以获得可索引性。

于 2019-10-19T22:33:49.790 回答
0

你可以unnest()

where exists (select 1
              from unnest(col) u(val)
              where u.val between 2 and 4
             )
于 2019-10-19T20:55:24.310 回答