В настоящее время я оптимизирую свои результаты поиска на jsonb-полях PostgreSQL. Я использую Postgres 9.6. Моя конечная цель - поиск по нескольким полям в моем jsonb-документе и ранжирование результатов в соответствии с их итогами во всех полях. Но я застрял, потому что функция ts_rank не использует мой индекс и сильно замедляет поиск. Вот минимальный пример:Индекс для ранжирования результатов поиска JSONB в PostgreSQL
CREATE TABLE book (
id BIGSERIAL NOT NULL,
data JSONB NOT NULL
);
CREATE INDEX book_title_idx
ON book USING GIN (to_tsvector('english', book.data ->> 'title'));
INSERT INTO book (data)
VALUES (CAST('{"title": "Cats"}' AS JSONB));
При попытке поиска в поле заголовка я использую этот запрос:
EXPLAIN ANALYZE
SELECT *
FROM (
SELECT
id,
data ->> 'title' AS title,
ts_rank(title_query, 'cat:*') AS score
FROM
book,
to_tsvector('english', data ->> 'title') title_query
WHERE title_query @@ to_tsquery('cat:*')
ORDER BY score DESC) a
WHERE score > 0
ORDER BY score DESC;
Без рейтинга поиска на моих реальных данных занимает < 1мса, с ранжированием это ~ 1800 мс. Это становится хуже, чем больше полей, которые я ищу. Мне нужен рейтинг только для того, чтобы сделать хиты в нескольких полях более ценными.
это большое улучшение +1 – e4c5
Это действительно наш поиск по 3 полям с 2000 мс до 500 мс. Я чувствую, что могу улучшить еще дальше. Я отправлю дополнительный вопрос для моего конкретного случая, так как вы ответили на мой оригинальный вопрос. Спасибо – SlideM
@ user7220980 вам, вероятно, не нужен фильтр 'score> 0', потому что вы уже выполняете соответствие FTS с' to_tsvector (...) @@ to_tsquery (...) '. Таким образом, нет необходимости использовать подзапрос. (но это, похоже, не является таким улучшением). – pozs