245

使用 Postgres 9.0,我需要一种方法来测试给定数组中是否存在值。到目前为止,我想出了这样的事情:

select '{1,2,3}'::int[] @> (ARRAY[]::int[] || value_variable::int)

但我一直在想应该有一个更简单的方法,我只是看不到它。这似乎更好:

select '{1,2,3}'::int[] @> ARRAY[value_variable::int]

我相信这就足够了。但是如果您有其他方法可以做到这一点,请分享!

4

7 回答 7

385

构造更简单ANY

SELECT value_variable = ANY ('{1,2,3}'::int[])

(括号之间)的右操作数ANY可以是集合(例如,子查询的结果)数组。有几种使用方法:

重要区别:数组运算符(<@, @>, &&et al.)期望数组类型作为操作数并在 PostgreSQL 的标准发行版中支持 GIN 或 GiST 索引,而ANY构造期望元素类型作为左操作数并且不支持这些索引。例子:

这些都不适用于NULL元素。测试NULL

于 2012-06-27T17:37:25.493 回答
118

当心我陷入的陷阱:当检查某个值是否存在于数组中时,你不应该这样做:

SELECT value_variable != ANY('{1,2,3}'::int[])

但使用

SELECT value_variable != ALL('{1,2,3}'::int[])

反而。

于 2013-04-12T10:04:51.017 回答
40

但如果您有其他方法,请分享。

您可以比较两个数组。如果左侧数组中的任何值与右侧数组中的值重叠,则返回 true。这有点骇人听闻,但它确实有效。

SELECT '{1}'   && '{1,2,3}'::int[];  -- true
SELECT '{1,4}' && '{1,2,3}'::int[];  -- true
SELECT '{4}'   && '{1,2,3}'::int[];  -- false
  • 在第一个和第二个查询中,值1在正确的数组中
  • 请注意,第二个查询是true,即使该值4未包含在正确的数组中
  • 对于第三个查询,左侧数组(即4)中没有值在右侧数组中,因此返回false
于 2014-10-08T20:42:06.100 回答
7

unnest也可以使用。它将数组扩展为一组行,然后简单地检查一个值是否存在,就像使用INor一样简单NOT IN

例如

  1. id => uuid

  2. exception_list_ids => uuid[]

select * from table where id NOT IN (select unnest(exception_list_ids) from table2)

于 2017-08-08T23:15:27.950 回答
7

嗨,一个对我有用,也许对某人有用

select * from your_table where array_column ::text ilike ANY (ARRAY['%text_to_search%'::text]);
于 2020-06-04T10:46:30.087 回答
3

在查找数组中是否存在元素时,需要正确转换才能通过 postgres 的 SQL 解析器。这是一个在连接子句中使用数组包含运算符的示例查询:

为简单起见,我只列出相关部分:

table1 other_name text[]; -- is an array of text

显示的 SQL 的连接部分

from table1 t1 join table2 t2 on t1.other_name::text[] @> ARRAY[t2.panel::text]

以下也有效

on t2.panel = ANY(t1.other_name)

我只是猜测需要额外的转换,因为解析不必获取表定义来确定列的确切类型。其他人请对此发表评论。

于 2017-11-01T20:49:07.207 回答
3

“任何”都很好用。只需确保 any 关键字位于等号的右侧,即出现在等号之后。

以下语句将抛出错误:错误:“任何”处或附近的语法错误

select 1 where any('{hello}'::text[]) = 'hello';

而下面的例子工作正常

select 1 where 'hello' = any('{hello}'::text[]);
于 2020-09-24T03:42:51.867 回答