前段时间, 一个线上项目忽然很卡, 通过监控, 发现内存很高, 果不其然在几个小时后, OOM. 虽说有人很快处理好了. 但我还是想站在我的角度, 对这件事发表一下自己的观点.
内存溢出, 多发生在项目上线后, 而且在系统开发阶段和单元测试阶段几乎不被发现. 这其实是和开发者习惯有关. 譬如一些空的引用, 就会占着茅厕不拉屎等等
而要搞明白这个过程, 不得不提一下 java 是如何管理内存的. 主要涉及到对象的分配和释放.
在 java 中, 内存分配是由程序完成的, 而释放, 是由垃圾回收机制自动完成的.
内存分配扯到各种 new 对象, 此处不多写, 主要谈谈 GC 过程 .
我用 idea 装了 Java VisualVM 插件 , 用自己的测试工程启动后, 可以看到这样一个界面, 说明插件安装成功, 已经成功监视到我的工程
我不是来讲这个插件如何使用的, 我本人也在学习阶段, 所以直接看本文重点
在我第一次看到这个图的时候, 恍然大明白, 原来之前看的 GC 分区, 就是这么回事. 但是过程是什么样的呢, 就这个图我做下说明 (其实是我自己在网上整理了一下, 然后讲出来, 加上自己的一些理解)
希望能对和我一样曾经徘徊在 GC 门口的人一点帮助.
图示, 在整个 GC 过程中, 大概有 3 个历程.
Eden Space: 新生
Old Gen: 老年
Metaspace: 持久代. 持久好啊 ^_^
新生代和老年代之间, 有 2 个 Survivor 区, 图里面为 S0,S1. 这两个作用是什么, 别着急, 咱一步步来, 要有前戏.
首先当对象被创建的时候, new 一个女朋友, 是每个程序猿的梦想. 但是在这里, 女朋友需要从相亲对象不断的跨越山河大海, 才能成为女朋友, 持续在一起. 我开辟一个主任务 (系统栈): 我要相亲, 媒婆给我找一些相亲对象来. 于是乎, 很多相亲对象被 new 了出来, 要大面撒网嘛. 所以很多各种模样的相亲对象就排着队进到 Eden 区, 高的, 矮的, 胖的, 瘦的, 瓜子脸, O 型腿, 什么样的都有.
护卫何在, 在. 去把这些矮的, 胖的, 长相怪异的, 都给我赶出门外, 还有媒婆你下次挑的时候, 长点眼睛. Eden:S 区默认大小是 8:1
于是一些看了一眼, 甚至看都没看一眼的垃圾对象被清了出去. 剩下的, 都还看的过去. 全部给我去 S0 房间待着啊, 进行第一轮考核. 此刻 S1 是空的.
此时 Eden 房间已经闲置了, 但是在整个项目运行期间, 只要有人进行任何操作, 都会不断的有新对象进来到内存中.
所以 Eden 很快又满了, 在经历了 S0 房间的筛选后, 一些人由于思想问题, 也要被赶出去, 同时呢 Eden 这一批也有留下的, 于是, S0 剩下的和 Eden 剩下的, 全都给我去 S1 待着去, 那里会继续审查. 为什么这批 S0 的已经审查过了, 还有继续审查呢, 那是因为现在网络这么发达, 太多东西都可以作假, 一次可能瞒混过关, 需要进行多次选择. 注意此刻 S0 是空的.(复制, 引用计数法. Scavenge GC)
当这批 S1 的检查完后, 去掉一些家底不干净的, 还留了一部分, 而新的 Eden 依旧有一批筛选后的, 这两部分人, 又全部进去 S0 再次给我检查, 身上有胎记的, 毛太长的, 有狐臭的等等都给我赶出去. 此刻 S1 是空的.(复制, 引用计数法. Scavenge GC)
当如此循环多次后, 筛选来筛选后, 发现某次 S0 或者 S1 挤满了, 不能再和新的 Eden 区剩下的人去挤进一个 S 房间了, 系统就认为这批相亲对象, 质量很高 (对象的引用一直存在), 全部移步到 Old Gen. 此刻 S0 和 S1 空了, 继续和 Eden 进行新的循环.
此刻我来到 Old Gen, 开始逐个进行洗脑, 这是个漫长的过程: 因为要成为我的女朋友, 要心甘情愿的洗衣做饭暖床等等. 过了很长一段时间的试恋爱后, Old Gen 房间太满了, 而且还有很多不同意以上条件的美女们, 我不能白养着啊, 不合适就走吧, 我不是慈善家. 都走后门出去啊, 别太惹人注目.
此处对应 GC 中, Eden 和 S 区调整不能腾出足够的空间时, 要进行的 FULL GC, 此时 JVM GC 停止所有在 heap 中 运行的线程并执行清除动作.(标记压缩 - 清除)
而经历了多次 FULL GC 还留下的, 我要把你们纳入后宫, 都去 Metaspace 吧. 我在那里等着你们. 那里有我喜欢的生活用品, 交通工具等. 几乎不会改变, 只会把一些旧的更换成新的. 只要我有肉吃, 就少不了你们的汤喝.
有几个点需要强调一下, 如果 Eden 中有极品美女, 是可以直接进入到 Old Gen 的. 对应一些大的对象, 直接进老年代.
以上只是一些总结, 随着学习的深入, 我会继续补充. 有写错的, 欢迎在评论区纠正. 哈哈, 第一次写这么长. 自我鼓励一下
来源: https://www.cnblogs.com/justtodo/p/11065223.html