Добро пожаловать в форум, Guest  >>   Войти | Регистрация | Поиск | Правила | В избранное | Подписаться
Все форумы / PostgreSQL Новый топик    Ответить
 btree-gist-индекс на int8[]: нет операторов...  [new]
Cyrax_02
Member

Откуда:
Сообщений: 1397
Задача: для быстрого поиска значений int8 в массиве int8[] построить совместный индекс на поля int4 и int8[].
Для построения совместного GIST-индекса используются расширения btree_gist и intarray.

Проблема в том, что для int8[] расширение intarray не создаёт GIST-операторов:
SQL Error [42704]: ОШИБКА: для типа данных bigint[] не определён класс операторов по умолчанию для метода доступа "gist"
Если для int8[] явно указать класс операторов gist__int_ops, получаем:
SQL Error [42804]: ОШИБКА: класс операторов "gist__int_ops" не принимает тип данных bigint[]
Если для int8[] явно указать класс операторов gist__intbig_ops, получаем:
SQL Error [42804]: ОШИБКА: класс операторов "gist__intbig_ops" не принимает тип данных bigint[]

P.S. Для int8[] GIN-оператор расширение intarray создаёт. Но с GIN-индексом на массиве можно будет проверять только одно значение на вхождение и всё. Т.е. желателен именно GIST-индекс.

Сообщение было отредактировано: 20 ноя 20, 01:16
20 ноя 20, 01:19    [22235807]     Ответить | Цитировать Сообщить модератору
 Re: btree-gist-индекс на int8[]: нет операторов...  [new]
Melkij
Member

Откуда: Санкт-Петербург
Сообщений: 1190
Cyrax_02
Для int8[] GIN-оператор расширение intarray создаёт

Нет. Это встроенный array_ops.
intarray даёт только int[], что чудесно видно по install скрипту.
Если вы почему-то решили, что gist__intbig_ops имеет отношение к bigint - вы невнимательно читаете документацию, где объясняется почему их два.
20 ноя 20, 12:11    [22235957]     Ответить | Цитировать Сообщить модератору
 Re: btree-gist-индекс на int8[]: нет операторов...  [new]
Cyrax_02
Member

Откуда:
Сообщений: 1397
Melkij
Если вы почему-то решили, что gist__intbig_ops имеет отношение к bigint - вы невнимательно читаете документацию, где объясняется почему их два.
Я понимаю, что к integer и bigint прямого отношения он не имеет (касается числа элементов в массиве, а не типа элементов массива).
Оба варианта GIST/gist__int_ops и GIST/gist__intbig_ops я привёл для "полноты картины".

Melkij
Cyrax_02
Для int8[] GIN-оператор расширение intarray создаёт.
Нет. Это встроенный array_ops.
> https://postgrespro.ru/docs/postgresql/13/gin-examples
> Также классы операторов GIN содержатся в следующих модулях contrib:
> intarray - Расширенная поддержка int[]


Melkij
intarray даёт только int[], что чудесно видно по install скрипту
Да, в справке об этом тоже упоминается, что только для int4[]
(правда, в описании модуля intarray об этом почему-то ни слова):

> https://postgrespro.ru/docs/postgresql/13/gist-examples
> Классы операторов GiST содержатся также и в следующих дополнительных модулях (contrib):
> intarray - RD-дерево для одномерных массивов значений int4

Тогда получается, что на int8[] построить GIST невозможно ? Без написания собственных операторов.
20 ноя 20, 14:08    [22236038]     Ответить | Цитировать Сообщить модератору
 Re: btree-gist-индекс на int8[]: нет операторов...  [new]
Cyrax_02
Member

Откуда:
Сообщений: 1397
автор
к integer и bigint прямого отношения он не имеет (касается числа элементов в массиве, а не типа элементов массива)
Вернее, так: названия этих классов операторов касаются числа элементов в массивах, а сами классы операторов различаются реализацией.

По поводу модуля intarray. Он создаёт классы операторов только для int4[]:
GIST: gist__int_ops и gist__intbig_ops
GIN: gin__int_ops

Также есть стандартный класс операторов array_ops, который работает с int2[], int4[] и int8[].
Т.е. для работы с int8[] придётся создавать GIN-индекс со стандартным классом операторов array_ops, который не поддерживает операцию @@.

Сообщение было отредактировано: 20 ноя 20, 15:09
20 ноя 20, 15:13    [22236079]     Ответить | Цитировать Сообщить модератору
 Re: btree-gist-индекс на int8[]: нет операторов...  [new]
Cyrax_02
Member

Откуда:
Сообщений: 1397
Здесь возникают такие вопросы:
1) Какой индекс на int8[] работает быстрее: GIN/array_ops или GIN/gin__int_ops ?
2) Какой индекс на int8[] занимает меньше места: GIN/array_ops или GIN/gin__int_ops ?

3) Что делает оператор @@ применительно к массивам ?
В справке он описывается только применительно к полнотекстовому поиску (соответствие) и геометрическим фигурам (геометрический центр).
Но применительно к массивам этот оператор не упоминается...

Сообщение было отредактировано: 20 ноя 20, 15:17
20 ноя 20, 15:22    [22236088]     Ответить | Цитировать Сообщить модератору
 Re: btree-gist-индекс на int8[]: нет операторов...  [new]
Melkij
Member

Откуда: Санкт-Петербург
Сообщений: 1190
Cyrax_02
Здесь возникают такие вопросы:
1) Какой индекс на int8[] работает быстрее: GIN/array_ops или GIN/gin__int_ops ?
2) Какой индекс на int8[] занимает меньше места: GIN/array_ops или GIN/gin__int_ops ?

Сложно сравнивать то, чего не существует. Повторю ещё раз:
CREATE OPERATOR CLASS gin__int_ops
FOR TYPE _int4 USING gin

Всё что есть про gin в intarray. _int4 = int4[]. Для int8[] в intarray нет ничего.

Cyrax_02
3) Что делает оператор @@ применительно к массивам ?
В справке он описывается только применительно к полнотекстовому поиску (соответствие) и геометрическим фигурам (геометрический центр).
Но применительно к массивам этот оператор не упоминается...

Не представляю, откуда вы этот оператор взяли.

Cyrax_02
Тогда получается, что на int8[] построить GIST невозможно ? Без написания собственных операторов.

Штатных нет.
20 ноя 20, 17:18    [22236160]     Ответить | Цитировать Сообщить модератору
 Re: btree-gist-индекс на int8[]: нет операторов...  [new]
Cyrax_02
Member

Откуда:
Сообщений: 1397
автор
3) Что делает оператор @@ применительно к массивам ?
В справке он описывается только применительно к полнотекстовому поиску (соответствие) и геометрическим фигурам (геометрический центр).
Но применительно к массивам этот оператор не упоминается...
Ага, это такой же оператор запроса, что и в случае с jsonb. Вводится тем же самым расширением intarray:
https://postgrespro.ru/docs/postgresql/13/intarray#id-1.11.7.27.8
integer[] @@ query_int → boolean
Массив удовлетворяет запросу? (см. ниже)

Операторы @@ и ~~ проверяют, удовлетворяет ли массив запросу, представляемому в виде значения специализированного типа данных query_int. Запрос содержит целочисленные значения, сравниваемые с элементами массива, возможно с использованием операторов & (AND), | (OR) и ! (NOT). При необходимости могут использоваться скобки. Например, запросу 1&(2|3) удовлетворяют запросы, которые содержат 1 и также содержат 2 или 3.

тот же результат, но с оператором запроса
SELECT message.mid FROM message WHERE message.sections @@ '1&2'::query_int;

По поводу GIN/array_ops или GIN/gin__int_ops напрашивается такой вывод.
Если не требуется оператор @@, то для массивов целых чисел лучше использовать стандартный GIN/array_ops:

1) GIN-индексы занимают меньше места + быстрее строятся
2) стандартный класс операторов [array_ops] позволяет работать с любыми типами (в т.ч. с int1, uint1, uint2, uint4, uint8 из расширения pg_uint) без приведения их к int4[] - а это экономия места за счёт малых размеров индекса

Но, судя по всему, GIN/gin__int_ops работает быстрее, чем стандартный GIN/array_ops.

Сообщение было отредактировано: 20 ноя 20, 17:33
20 ноя 20, 17:28    [22236163]     Ответить | Цитировать Сообщить модератору
 Re: btree-gist-индекс на int8[]: нет операторов...  [new]
Cyrax_02
Member

Откуда:
Сообщений: 1397
Melkij
Cyrax_02
Здесь возникают такие вопросы:
1) Какой индекс на int8[] работает быстрее: GIN/array_ops или GIN/gin__int_ops ?
2) Какой индекс на int8[] занимает меньше места: GIN/array_ops или GIN/gin__int_ops ?
Сложно сравнивать то, чего не существует. Повторю ещё раз:
CREATE OPERATOR CLASS gin__int_ops
FOR TYPE _int4 USING gin
Всё что есть про gin в intarray. _int4 = int4[]. Для int8[] в intarray нет ничего.
Так GIN/array_ops - это не intarray, а стандартный класс операторов с массивами.
И с int8[] он работает, и с uint1[] работает...

Melkij
Не представляю, откуда вы этот оператор взяли.
Видно, что модулем intarray вы не пользовались ))

https://postgrespro.ru/docs/postgresql/13/intarray#id-1.11.7.27.8
Модуль intarray поддерживает индексы для операторов &&, @>, <@ и @@, а также обычную проверку равенства массивов.
Т.е. разница со стандартным GIN-индексом array_ops только в операторе @@.

Сообщение было отредактировано: 20 ноя 20, 17:40
20 ноя 20, 17:35    [22236166]     Ответить | Цитировать Сообщить модератору
 Re: btree-gist-индекс на int8[]: нет операторов...  [new]
Melkij
Member

Откуда: Санкт-Петербург
Сообщений: 1190
Cyrax_02
Melkij
пропущено...
Сложно сравнивать то, чего не существует. Повторю ещё раз:
CREATE OPERATOR CLASS gin__int_ops
FOR TYPE _int4 USING gin
Всё что есть про gin в intarray. _int4 = int4[]. Для int8[] в intarray нет ничего.
Так GIN/array_ops - это не intarray, а стандартный класс операторов с массивами.
И с int8[] он работает, и с uint1[] работает...

Я не спорю что GIN/array_ops существует. А сравнивать-то с чем?

Cyrax_02
Melkij
Не представляю, откуда вы этот оператор взяли.
Видно, что модулем intarray вы не пользовались ))

Когда мешает - видел. Да, оказалось я уже спилил этот extension когда проверял список операторов.
20 ноя 20, 17:42    [22236168]     Ответить | Цитировать Сообщить модератору
 Re: btree-gist-индекс на int8[]: нет операторов...  [new]
Cyrax_02
Member

Откуда:
Сообщений: 1397
Melkij
Cyrax_02
пропущено...
Так GIN/array_ops - это не intarray, а стандартный класс операторов с массивами.
И с int8[] он работает, и с uint1[] работает...
Я не спорю что GIN/array_ops существует. А сравнивать-то с чем?
intarray-вский GIN/gin__int_ops со стандартным всеядным GIN/array_ops применительно к массивам целых чисел.

Сообщение было отредактировано: 20 ноя 20, 17:45
20 ноя 20, 17:47    [22236173]     Ответить | Цитировать Сообщить модератору
 Re: btree-gist-индекс на int8[]: нет операторов...  [new]
Melkij
Member

Откуда: Санкт-Петербург
Сообщений: 1190
Cyrax_02
Melkij
пропущено...
Я не спорю что GIN/array_ops существует. А сравнивать-то с чем?
intarray-вский GIN/gin__int_ops со стандартным всеядным GIN/array_ops применительно к массивам целых чисел.

Так ведь не существует gin__int_ops для int8[]
20 ноя 20, 19:20    [22236196]     Ответить | Цитировать Сообщить модератору
 Re: btree-gist-индекс на int8[]: нет операторов...  [new]
Cyrax_02
Member

Откуда:
Сообщений: 1397
Melkij
Так ведь не существует gin__int_ops для int8[]
Вот и получили мы infinite loop ))
Речь о массивах, для которых существуют оба класса операторов. Таковыми являются только int4[].
20 ноя 20, 20:16    [22236219]     Ответить | Цитировать Сообщить модератору
 Re: btree-gist-индекс на int8[]: нет операторов...  [new]
Melkij
Member

Откуда: Санкт-Петербург
Сообщений: 1190
Да нет, явно дважды было указано именно int8.
Cyrax_02
Здесь возникают такие вопросы:
1) Какой индекс на int8[] работает быстрее: GIN/array_ops или GIN/gin__int_ops ?
2) Какой индекс на int8[] занимает меньше места: GIN/array_ops или GIN/gin__int_ops ?
20 ноя 20, 22:19    [22236251]     Ответить | Цитировать Сообщить модератору
 Re: btree-gist-индекс на int8[]: нет операторов...  [new]
Cyrax_02
Member

Откуда:
Сообщений: 1397
Это не я.

Сообщение было отредактировано: 21 ноя 20, 01:30
21 ноя 20, 01:34    [22236305]     Ответить | Цитировать Сообщить модератору
Все форумы / PostgreSQL Ответить