mysql流式查询_Mybatis流式查询避免OOM

更新时间:2023-06-08 20:02:31 阅读: 评论:0

mysql流式查询_Mybatis流式查询避免OOM
前⾔
当指定查询数据过⼤时,我们⼀般使⽤分页查询的⽅式,⼀页⼀页的将数据放到内存处理。但有些情况不需要分页的⽅式查询数据,如果⼀下⼦将数据全部加载出来到内存中,很可能会发⽣OOM。这时我们可以使⽤流式查询解决问题。
⾮流式查询
为了更好的复现问题,将jvm参数,最⼤堆设置成212M。使⽤mysql数据库,表⼤⼩为730MB。
⾮流式查询表⾥所有数据代码
List infoPOs = infoMapper.lectList(new EntityWrapper<>());
beem
通过查看idea控制台,很快出现了内存溢出。
通过jconsole⼯具,查看内存使⽤情况
在14.26,发现内存直接被释放了。
流式查询
流式查询表⾥所有数据代码heart and soul
@Select("lect * from t_iot")
@Options(resultSetType = ResultSetType.FORWARD_ONLY, fetchSize = Integer.MIN_VALUE)
@ResultType(InfoPO.class)
void lectAutoList(ResultHandler handler);
infoMapper.lectAutoList(resultContext -> {
教师节英文祝福语简短});
通过查看idea控制台,程序运⾏正常
在通过jconsole⼯具,查看内存使⽤情况
发现内存消耗处于平稳状态。
流式查询原理sweet love什么意思
查看源码可知,我们使⽤流式查询时,必须要满⾜以下3个条件
/**
* We only stream result ts when they are forward-only, read-only, and the
* fetch size has been t to Integer.MIN_VALUE
*
* @return true if this result t should be streamed row at-a-time, rather
六级 时间* than read all at once.
*/
protected boolean createStreamingResultSet() {
return ((ResultType() == Type.FORWARD_ONLY) && (sultSetConcurrency ==
java.sql.ResultSet.CONCUR_READ_ONLY)
&& (ResultFetchSize() == Integer.MIN_VALUE));
}
resultSetConcurrency=ResultSet.CONCUR_READ_ONLY 设置只读结果集
resultSetType = ResultSetType.FORWARD_ONLY 设置结果集的游标只能向下滚动
fetchSize = Integer.MIN_VALUE 设置fetch size为int的最⼩值,这⾥和oracle/db2有区别.
Oracle/db2是从服务器⼀次取出fetch size 条记录放在客户端,客户端处理完成⼀个批次后再向服务器取下⼀个批次,直到所有数据处理完成。
mysql在执⾏()⽅法时,会通过数据库连接⼀条⼀条的返回。MySQL按照⾃⼰的节奏不断的把buffer写回⽹络中。flush buffer的过程是阻塞式的,也就是说如果⽹络中发⽣了拥塞,nd buffer被填满,会导致buffer⼀直flush不出去,那MySQL的处理线程会阻塞,从⽽避免数据把客户端内存撑爆。
设置三个参数之后,断点进⼊到了流式返回结果集ResulttRowsStreaming。commander
ResultSet数据返回的结果,对象有3种实现⽅式
uva
ResulttRowsStatic 静态结果集,默认的查询⽅式,普通查询
ResulttRowsCursor 游标结果集,服务器端基于游标查询
跟我学
ResulttRowsStreaming 动态结果集,流式查询
查看ResulttRowsStatic类注释
/**
* Reprents an in-memory result t
*/
public class ResulttRowsStatic extends AbstractResulttRows implements ResulttRows {
表⽰放在内存中的结果集。
查看ResulttRowsStreaming类注释
/**
* Provides streaming of Resultt rows. Each next row is consumed from the
* input stream only on {@link #next()} call. Consumed rows are not cached thuswholeheartedly
* we only stream result ts when they are forward-only, read-only, and the
* fetch size has been t to Integer.MIN_VALUE (rows are read one by one).
你叫什么名字 用英语怎么说 *
* @param
* ProtocolEntity type
*/
public class ResulttRowsStreaming extends AbstractResulttRows implements ResulttRows {
提供了Resultt⾏的流。获取下⼀⾏都是从仅在{@link #next()}调⽤时输⼊流。因此不会缓存已使⽤的⾏。我们只在结果集只有前进、只读和时才流结果集获取⼤⼩已设置为整数。MIN_VALUE(逐个读取⾏)。
总结
之前使⽤过db2处理流式查询,设置的fetch size为100,没有问题。这次使⽤mysql刚开始时也设置的100,发现内存溢出了,后来在⽹上看到mysql流式获取数据的坑,debug进去果然没⾛到ResulttRowsStreaming类,设置fetch size 参数为Integer.MIN_VALUE后,才进了ResulttRowsStreaming类。

本文发布于:2023-06-08 20:02:31,感谢您对本站的认可!

本文链接:https://www.wtabcd.cn/fanwen/fan/90/138457.html

版权声明:本站内容均来自互联网,仅供演示用,请勿用于商业和其他非法用途。如果侵犯了您的权益请与我们联系,我们将在24小时内删除。

上一篇:nginx的rver配置
下一篇:费用签报模板
标签:内存   查询   结果   流式   数据   查看   设置
相关文章
留言与评论(共有 0 条评论)
   
验证码:
Copyright ©2019-2022 Comsenz Inc.Powered by © 专利检索| 网站地图