Какой самый эффективный способ переписать большое предложение IN? - PullRequest
0 голосов
/ 09 октября 2018

Я написал API, используя go and gorm, который выполняет вычисления в нашей базе данных и возвращает результаты.

Я только что достиг предела параметра для условия IN при использовании агрегата.Пример запроса:

SELECT SUM(total_amount) from Table where user_id in(...70k parameters) group by user_id

В одном из моих текущих краевых случаев> 65535 идентификаторов пользователей, поэтому мой клиент Postgres выдает ошибку:

got 66037 parameters but PostgreSQL only supports 65535 parameters

I'mне уверен, что лучший способ подойти к этому.Тот, который будет обрабатывать большое количество параметров для этого граничного случая, но не влияет на мой типичный вариант использования.Должен ли я разделять идентификаторы на части и выполнять несколько запросов, сохраняя их в памяти, пока у меня не появятся все необходимые данные?Используйте ANY(VALUES) ...

Очевидно, что из запроса у меня очень ограниченные знания Postgres, поэтому любая помощь будет невероятно оценена.

1 Ответ

0 голосов
/ 09 октября 2018

Вы можете заменить user_id IN (value [, ...]) одним из:

user_id IN (subquery)
user_id = ANY (subquery)
user_id = ANY (array expression)

Ни подзапросы, ни массивы не имеют одинакового ограничения.Кратчайший синтаксис ввода:

user_id = ANY ('{1,2,3}'::int[])  -- make array type match type of user_id

Подробности и дополнительные параметры:

Или вы можете создать (временную) таблицу tmp_usr(user_id int), импортировать в нее, возможно, с SQL COPY или psql \copy вместо INSERT для лучшегопроизводительность с очень большими сетами , а затем присоединение к таблице, например:

SELECT SUM(total_amount)
FROM   tbl
JOIN   tmp_usr USING (user_id)
GROUP  BY user_id;

BTW, GROUP BY user_id без включения user_id в SELECTсписок выглядит подозрительно.Может быть упрощенным примером запроса.

...