Използването на setFirstResult и setMaxResults е единствената ви опция, за която знам.
Традиционно набор от резултати с възможност за превъртане би прехвърлял редове на клиента само според изискванията. За съжаление MySQL Connector/J всъщност го фалшифицира, той изпълнява цялата заявка и я транспортира до клиента, така че драйверът всъщност има целия набор от резултати, зареден в RAM и ще ви го подаде капково (доказателство от проблемите ви с липса на памет) . Имахте правилната идея, това са просто недостатъци в MySQL java драйвера.
Не намерих начин да заобиколя това, затова заредих големи парчета, използвайки обикновените методи setFirst/max. Съжалявам, че съм носител на лоши новини.
Просто се уверете, че използвате сесия без състояние, така че да няма кеш на ниво сесия или мръсно проследяване и т.н.
РЕДАКТИРАНЕ:
Вашата UPDATE 2 е най-доброто, което ще получите, освен ако не излезете от MySQL J/Connector. Въпреки че няма причина да не можете да увеличите лимита на заявката. При условие, че имате достатъчно RAM, за да държите индекса, това би трябвало да е малко евтина операция. Бих го модифицирал леко и бих грабвал партида наведнъж и бих използвал най-високия идентификатор на тази партида, за да взема следващата партида.
Забележка:това ще работи само ако други_условия използвайте равенство (не са разрешени условия за диапазон) и задайте последната колона на индекса като id .
select *
from person
where id > <max_id_of_last_batch> and <other_conditions>
order by id asc
limit <batch_size>