在上篇文章<线上服务器内存不断飙升定位>基础上继续进行,问题定位到了,那就开始优化,本地缓存+线程池合理使用两大块;本地缓存已经在上篇文章说明了<项目中如何整合本地缓存>,改造上线后,在内存高的情况下,再次dump了内存快快照,发现内存泄露的情况好很多
但是我还是发现一个现象就是每次服务器重启,内存都是一个直线上升的状态,直接先飙到快60%,然后才稳定下来,慢慢再增加
这就很纳闷了,思考呗,啥原因导致的,边查资料边动手试一下;
登录线上服务器,jmap -heap 17,执行命令,如下:
Heap Configuration:
MinHeapFreeRatio = 40 //JVM最小空闲比率 可由-XX:MinHeapFreeRatio=<n>参数设置, jvm heap 在使用率小于 n 时 ,heap 进行收缩
MaxHeapFreeRatio = 70 //JVM最大空闲比率 可由-XX:MaxHeapFreeRatio=<n>参数设置, jvm heap 在使用率大于 n 时 ,heap 进行扩张
MaxHeapSize = 5704253440 (5440.0MB) //JVM堆的最大大小 可由-XX:MaxHeapSize=<n>参数设置
NewSize = 1363144 (1.2999954223632812MB) //JVM新生代的默认大小 可由-XX:NewSize=<n>参数设置
MaxNewSize = 3422552064 (3264.0MB) //JVM新生代的最大大小 可由-XX:MaxNewSize=<n>参数设置
OldSize = 5452592 (5.1999969482421875MB) //JVM老生代的默认大小 可由-XX:OldSize=<n>参数设置
NewRatio = 2 //新生代:老生代(的大小)=1:2 可由-XX:NewRatio=<n>参数指定New Generation与Old Generation heap size的比例
SurvivorRatio = 8 //survivor:eden = 1:8,即survivor space是新生代大小的1/(8+2)[因为有两个survivor区域] 可由-XX:SurvivorRatio=<n>参数设置
MetaspaceSize = 536870912 (512.0MB) //元空间的默认大小,超过此值就会触发Full GC 可由-XX:MetaspaceSize=<n>参数设置 //类指针压缩空间的默认大小 可由-XX:CompressedClassSpaceSize=<n>参数设置
CompressedClassSpaceSize = 1073741824 (1024.0MB) //类指针压缩空间的默认大小 可由-XX:CompressedClassSpaceSize=<n>参数设置
MaxMetaspaceSize = 536870912 (512.0MB) //元空间的最大大小 可由-XX:MaxMetaspaceSize=<n>参数设置
G1HeapRegionSize = 2097152 (2.0MB) //使用G1垃圾收集器的时候,堆被分割的大小 可由-XX:G1HeapRegionSize=<n>参数设置
Heap Usage:
G1 Heap:
regions = 2720
capacity = 5704253440 (5440.0MB)
used = 843304696 (804.2380294799805MB)
free = 4860948744 (4635.7619705200195MB)
14.783787306617288% used
G1 Young Generation:
Eden Space:
regions = 218
capacity = 2403336192 (2292.0MB)
used = 457179136 (436.0MB)
free = 1946157056 (1856.0MB)
19.022687609075042% used
Survivor Space:
regions = 17
capacity = 35651584 (34.0MB)
used = 35651584 (34.0MB)
free = 0 (0.0MB)
100.0% used
G1 Old Generation:
regions = 195
capacity = 3265265664 (3114.0MB)
used = 348376824 (332.23802947998047MB)
free = 2916888840 (2781.7619705200195MB)
10.669172430314081% used
内存使用情况都算正常,但是我注意到一个点,NewSize这个参数太小了,会不会是JVM启动时分配的新生代内存太小,导致的服务器启动后,随着服务的调用导致的内存刚开始急速上升,如果我提前指定一个大小让其使用,内存会不会刚开始不会上升那么快,抱着试一试的态度,我添加了参数-XX:NewSize=1024M或者-Xmn1024m ,重启服务器
维持在了30%左右,看来还是有点作用的,结束;
线程池使用优化对比
内存也随之降低一些
关于GC日志分析调优的可以参考这篇文章:
https://juejin.cn/post/6844904175571042312#heading-14