Java 从mybatis读取数据时发出OOM

Java 从mybatis读取数据时发出OOM,java,mybatis,Java,Mybatis,尝试使用MyBatis读取大型结果集时,我遇到OOM错误。 MyBatis版本3.5 我想在光标上迭代,而不是加载整个查询结果。 是否有人有从mybatis select返回光标而不是返回整个结果的工作示例 [java]严重:内存使用率低,降落伞不存在,您的系统可能开始出现故障。 [java]java.lang.OutOfMemoryError:java堆空间 [java]AsyncLogger错误处理事件seq=0,value='null': [java]java.lang.OutOfMemo

尝试使用MyBatis读取大型结果集时,我遇到OOM错误。 MyBatis版本3.5 我想在光标上迭代,而不是加载整个查询结果。 是否有人有从mybatis select返回光标而不是返回整个结果的工作示例

[java]严重:内存使用率低,降落伞不存在,您的系统可能开始出现故障。 [java]java.lang.OutOfMemoryError:java堆空间 [java]AsyncLogger错误处理事件seq=0,value='null': [java]java.lang.OutOfMemoryError:java堆空间 [java]06 Sep 2020 05:34:34682[错误]http-nio-0.0.0-8243-ClientPoller-1 org.apache.tomcat.util.net.niodendpoint: [java]java.lang.OutOfMemoryError:java堆空间 [java]位于java.util.Collections$UnmodifiableCollection.iteratorCollections.java:1043~[?:?] [java]位于org.apache.tomcat.util.net.NioEndpoint$Poller.timeoutNioEndpoint.java:1471~[Bobcat-2.2.jar:?] [java]位于org.apache.tomcat.util.net.NioEndpoint$Poller.runNioEndpoint.java:1265~[Bobcat-2.2.jar:?] [java]位于java.lang.Thread.runThread.java:834[?:?] ReaderDao.xml

<select id="downloadelements" resultMap="elementMap">
    select *
    from sample_table
    where element_timestamp between #{startTime} and #{endTime}
    and status=#{status}
</select>
ReaderDao.java

public interface ReaderDao {
Cursor<Element> downloadElements(final @NotNull @Param("startTime") ZonedDateTime startTime,
                                                final @NotNull @Param("endTime") ZonedDateTime endTime,
                                                final @NotNull @Param("status") String status);
}

数据库:Aurora PostgreSQL

Cursor<Element> elementList = downloadElements(start, end, status);
Iterator<Element> elementIterator = elementList.iterator();
while (elementIterator.hasNext()) {
    Element element = ElementIterator.next();
    log.info(element.toString());
}
正如@ave所指出的,您很可能希望实现结果分页。这通常是通过使用ORDER by element_timestamp LIMIT OFFSET或使用。这两种方法中的任何一种都会将较小批次的结果加载到内存中,通过允许GC分别释放每个批次,从而避免OOME


但是,应该注意,有时增加可用堆内存是最简单的解决方案。RAM通常比程序员的时间要便宜,因此,也许您应该首先估计您要处理多少条记录以及需要多少内存。

显示导致内存消耗高的代码,否则我们必须猜测您在做什么。我添加了不起作用的代码。我不知道如何从select语句返回游标。我在文档中找不到多少信息。目标是不要一次性从数据库读取整个数据,因为这必然会导致OOM错误。请添加1结果映射元素映射,2代码处理光标,3数据库版本和4驱动程序版本。我已经添加了详细信息。我不确定驱动程序版本是什么。pgjdbc目前似乎不支持流式处理结果集。有一个开放的增强。谢谢我会尝试键集分页。