Postgres - 函数返回2个ARRAY的交集?

Ror*_*ory 32 sql postgresql

在postgresql中,如果两个数组具有公共成员,即它们重叠,则可以使用&&运算符返回t(true).是否有一个函数/运算符将返回那些常见成员?

即这样的事情

select arrray_intersection(ARRAY[1, 4, 2], ARRAY[2, 3]);
ARRAY[2]
Run Code Online (Sandbox Code Playgroud)

bar*_*art 55

从8.4开始,Postgres中有一些有用的内置函数,它们使第一个答案的函数更容易,也可能更快(这就是EXPLAIN告诉我的,无论如何:"(cost = 0.00..0.07 rows = 1 width = 64)"对于这个查询vs ."(成本= 0.00..60.02行= 1宽度= 64)"原始的一个).

简化的代码是:

SELECT ARRAY
    (
        SELECT UNNEST(a1)
        INTERSECT
        SELECT UNNEST(a2)
    )
FROM  (
        SELECT  array['two', 'four', 'six'] AS a1
              , array['four', 'six', 'eight'] AS a2
      ) q;
Run Code Online (Sandbox Code Playgroud)

是的,你可以把它变成一个功能:

CREATE FUNCTION array_intersect(anyarray, anyarray)
  RETURNS anyarray
  language sql
as $FUNCTION$
    SELECT ARRAY(
        SELECT UNNEST($1)
        INTERSECT
        SELECT UNNEST($2)
    );
$FUNCTION$;
Run Code Online (Sandbox Code Playgroud)

你可以称之为

SELECT array_intersect(array['two', 'four', 'six']
                     , array['four', 'six', 'eight']);
Run Code Online (Sandbox Code Playgroud)

但你也可以把它称为内联:

 SELECT array(select unnest(array['two', 'four', 'six']) intersect
              select unnest(array['four', 'six', 'eight']));
Run Code Online (Sandbox Code Playgroud)

  • 为了帮助优化,您可以将“array_intersect”函数标记为“IMMUTABLE”。 (3认同)

dwc*_*dwc 22

尝试&而不是&&

有关更多信息,请参阅PostgreSQL文档.

  • 请注意,这仅适用于整数数组. (6认同)
  • 经过测试,库存不起作用,需要安装扩展才能使其正常工作.但无论如何+1. (3认同)

mnv*_*mnv 6

如果您不介意安装扩展,则intarray 扩展提供了&操作员来执行此操作,正如@dwc 指出的那样。:

SELECT ARRAY[1, 4, 2] & ARRAY[2, 3];
Run Code Online (Sandbox Code Playgroud)

返回{2}

  • 您使用的是哪个 postgresql 版本?在 9.6 中,我收到以下错误,并且在文档中也找不到它。或者我在这里做错了什么?```错误:运算符不存在:整数[] & 整数[] 第1 行:SELECT ARRAY[1,4,2] & ARRAY[2,3] ^ 提示:没有运算符匹配给定的名称和参数类型)。您可能需要添加显式类型转换。``` (2认同)
  • 啊,等等,根据 https://www.postgresql.org/docs/current/static/intarray.html,它是 postgresql 的扩展。值得一提的是。 (2认同)

nca*_*ank 5

一种方法

SELECT ARRAY( SELECT * FROM UNNEST( $1 ) WHERE UNNEST = ANY( $2 ) );
Run Code Online (Sandbox Code Playgroud)

  • 这对我来说非常有效,因为它保留了顺序。谢谢你! (2认同)