Поиск позиции значения в массивах PostgreSQL - PullRequest
19 голосов
/ 10 января 2012

Как я могу получить позицию значения в массивах PostgreSQL? Есть метод .index() для Python и функция array_search() для PHP, но я не могу найти такую ​​функцию для PostgreSQL. Должен ли я написать хранимую функцию для этого? Я предпочитаю решать с помощью встроенной функции.

Ответы [ 3 ]

29 голосов
/ 10 января 2012

Документация рекомендует с использованием функции generate_subscripts.Приведенная ниже функция эмулирует PHP array_search:

CREATE FUNCTION array_search(needle ANYELEMENT, haystack ANYARRAY)
RETURNS INT AS $$
    SELECT i
      FROM generate_subscripts($2, 1) AS i
     WHERE $2[i] = $1
  ORDER BY i
$$ LANGUAGE sql STABLE;

. Возвращает индекс первого совпадения, если таковой имеется.Если вы хотите все совпадения, просто измените RETURNS INT на RETURNS SETOF INT.Эта функция, как есть, возвращает NULL, если совпадение не найдено.

Эта функция работает только с одномерными массивами.

Также имейте в виду, что array_search(NULL, a) всегда возвращает NULL, даже если массив содержит нулевые элементы:

> SELECT array_search(null, array[1, 2, null, 4]);
 array_search 
--------------

(1 row)

Это связано с тем, что SQL считает NULL = NULL неизвестным (т.е. NULL).Смотрите функции-сравнения .Если вы хотите, чтобы array_search мог найти NULL элементов, измените

     WHERE $2[i] = $1

на

     WHERE $2[i] IS NOT DISTINCT FROM $1
13 голосов
/ 21 ноября 2016

Начиная с версии 9.5 , имеются встроенные функции: array_position() и array_positions() для поиска по ключу массива (только первое вхождение) или ключей (все вхождения) по значению.

Эти функции поддерживают тип anyarray.

5 голосов
/ 26 июля 2013

Для целочисленных массивов * только 1001 * вы можете использовать значительно более быструю функцию idx из intarray связанного расширения .

Эта функция не была обобщенак сожалению, он поддерживает все типы массивов, поэтому вы застряли с очень медленным подходом SQL для других массивов.

Добро пожаловать на сайт PullRequest, где вы можете задавать вопросы и получать ответы от других членов сообщества.
...