在Postgres中检查数组中是否存在多个值

10

检查一个值是否存在于数组中非常简单。例如,以下代码将返回true。

SELECT 'hello' = ANY(ARRAY['hello', 'bees'])

如果我想检查数组中是否存在多个值,该怎么办呢?例如,如果我想要在数组中返回true,当'hello'或'bye'存在于数组中时。我想要做的事情类似于:

SELECT ['hello', 'bye'] = ANY(ARRAY['hello', 'bees'])

但是似乎不起作用。

编辑:

我还想弄清楚如何检查数组中是否存在多个具有共同前缀的值。

例如,如果我想返回true,如果数组包含任何具有“hello”前缀的元素。因此,我基本上想要像这样的东西

SELECT ARRAY['hello%'] && ARRAY['helloOTHERSTUFF']

确切地说,


1
ARRAY['hello', 'bye'] && ARRAY['hello', 'bees'] - Abelisto
谢谢!如果多个值跨越了具有相同前缀的多个事物怎么办?例如,我想匹配数组中以“hello”开头的任何值。例如,我想要类似于ARRAY ['hello'] && ARRAY ['helloOTHERSTUFF']这样的东西是真实的。我还将编辑原始帖子。 - Vincent
1
对于这种任意的情况,您需要使用unnest()将两个数组转换为记录集,然后适当地JOIN它们。您可以使用array()将其转换回数组。 - Jim Nasby
啊,我希望能做类似于 field_name ILIKE 'hello%' 的东西,但是针对数组。这不可能吗? - Vincent
如果您想将单个值与模式数组进行比较(类似于any但使用like而不是=),则可以实现,但反之则不行。对于两个(或多个)数组的复杂比较的一般模式是 exists 1 from unnest(<array1>) as t1(x1) join unnest(<array2>) as t2(x2) on (<join condition>),其中 <join condition> 对于您的示例可能是 x1 ilike x2 - Abelisto
1个回答

12

要检查数组中的任何元素是否存在于另一个数组中,请使用重叠&&操作符,如下所示:

SELECT ARRAY[1,4,3] && ARRAY[2,1] -- true

要检查每个数组元素是否匹配特定模式,您可以使用 unnest(anyarray)(提取数组元素)函数与LIKE或POSIX正则表达式(应用模式匹配)以及聚合bool_and(expression) - 执行按位AND运算符并返回一行输出。 测试用例: 我已将数组元素放在单独的行中,以澄清哪些比较为真,哪些为假。
SELECT bool_and(array_elements)
FROM (
  SELECT unnest(
    ARRAY[
     'hello', -- compared with LIKE 'hello%' yields true
     'helloSOMething', -- true
     'helloXX', -- true
     'hell', -- false
     'nothing' -- false
    ]) ~~ 'hello%'
  ) foo(array_elements); 

因此,如果任何一个比较结果为假,则bool_and(array_elements)将返回假。

注意: 如果您需要将数组与多个模式进行比较,则可以使用POSIX比较并使用|代替。例如,假设我们想找出数组的每个元素是否以hellonot单词开头:

SELECT bool_and(array_elements)
FROM (
  SELECT unnest(
    ARRAY[
     'hello', -- true
     'helloSOMething', -- true
     'helloXX', -- true
     'hell', -- false (doesn't start with neither "hello" nor "not")
     'nothing' -- true (starts with not)
    ]) ~ '^hello|not' -- note the use of ~ instead of ~~ as earlier (POSIX vs LIKE)
  ) foo(array_elements); 

注意:如果处理文本并且其中一个ARRAY来自聚合,则可能需要将底层数据转换为“text”:ARRAY_AGG(DISTINCT tbl.col::text) && ARRAY['x', 'y',..] - Rafs

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接