Scala Slick Lazy Fetch - программирование
Подтвердить что ты не робот

Scala Slick Lazy Fetch

Я хочу иметь возможность извлекать все записи из очень большой таблицы с помощью Slick. Если я попытаюсь сделать это через foreach, для или списка выборки; Я получаю исключение из памяти.

Можно ли использовать "курсоры" с Slick или ленивой загрузкой, которые только при необходимости извлекают объект, уменьшая объем используемой памяти?

4b9b3361

Ответ 1

Не уверен, что вы понимаете под курсорами, но вы можете получить частичные данные с помощью разбивки на страницы:

query.drop(0).take(1000) will take the first 1000 records

query.drop(1000).take(1000) will take from 1001 to 2000 lines of the table.

Но эффективность этого запроса будет зависеть от вашей базы данных, если она будет ее поддерживать, если таблица правильно проиндексирована.

Ответ 2

вы можете использовать комбинацию iterator, которая возвращает итератор:

 val object = Objects.where(...).map(w => w).iterator()

и группу:

val chunkSize = 1000
val groupedObjects = objects.grouped(chunkSize)
groupedObjects.foreach {objects => objects.par.map(h => doJob(h))}

как подскажите в этом ответе

Ответ 3

Ответ

dirceusemighini правильный. Я столкнулся с аналогичной проблемой несколько дней назад из-за неправильного предположения о Query.list(), поэтому я могу дать еще несколько контекстов. С справки Slick:

"Запросы выполняются с использованием методов, определенных в типе Invoker (или UnitInvoker для безпараметрических версий). Существует неявное преобразование из Query, поэтому вы можете выполнить любой запрос напрямую. Наиболее распространенным сценарием использования является чтение полного набора результатов в строгую коллекцию со специальным методом, таким как список или общий метод, с помощью которого можно создавать любые коллекции"

Действительно, Query.list() загружает полный набор результатов в память. Имея это в виду, вы можете иметь несколько подходов к своей проблеме.