闲聊:
一个cpu在同一时刻只能有一个线程,然后不断切换
,StringSream简洁好用
lambda 是一个匿名内部类,里面变量一定final 或者static,不然生命周期发生改变
#引用计数,无法定位相互引用的垃圾,jvm使用根可达算法new xx是根
1.G1垃圾回收器,jdk11 13 10种(自己挑) -->现在没有人用–>zgc与shenandoah竞争中 epsilon用于jdk11测试
//win直接可查看是哪个垃圾回收器,linux没有显示
java -XX:+PrintCommandLineFlags -version
//linux arthas可以查看,只是代表他的文件名
cd ar*bin
//g1:逻辑分代,物理不分代(之前是分代模型), zgc分代
//jdk1.8默认的ps+po
//scavenge(捡垃圾)
//cms
2.cms (可以解决ps+po卡顿的问题,线程角度,使用并发 gc与工作线程同时进行) 淘宝的fullgc 需要3天卡顿
//没有任何一款垃圾收集器会没有stw stop the world(cms大大降低stw的时间)
初始标记(stw,main对象初始new出来的对象)---->
并发标记(去一边标记,一边回收,程序会改成垃圾,或者不是垃圾变垃圾)
重新标记(remark, stw把漏标和错标的重新标记)
--->并发清理(全部有某个标记的清理掉,三色标记法)
jvm图24
jvm图25(根可达)
3.G1 解决之前垃圾回收器的问题: 操作必须扫描整个老年代,不适合大内存, 几百g用G1
旧机器使用Serial GC :
Parallel GC:计算
PN+CMS :内存10g节省内存
G1: 空间换时间
4,g1的分区(内存不是连续的分配的了) PN+CMS加点10%-15%内存+G1 响应时间成倍减少(自己可以决定新生代的比例)
jvm26
//90%的游戏后端是java写的!!!,腾讯c++ 昆仑万维
1.回收的时候只需要找到哪些最大块垃圾回收(放到ColletionSet)(使用复制到旁边的区,再压缩)
2.H区 一个对象占很大 Humongous , Y区=SurvivoEden
3.YGC 是由年轻代占比决定的 young,G1调优参数比较少,比较好调
4.内存占用超过45%,会启动 MixedGC(类似CMS 并发回收 一边工作一边回收)
5.上一次垃圾回收时间决定下一次年轻代的数量
5.(面试)G1有FullGC
答:有,尽量不让G1产生FullGC
6.G1并发标记(并发会导致错标和漏标)三色标记法
白色: 未被标记
灰色:自身被标记,成员变量未被标记
黑色:自身和成员变量都被标记
漏标只有一种情况: remark阶段,本来灰色指向白色(引用消失),黑色指向白色,变成直接把白色回收掉
解决方案:
1.incremental update(cms算法)增量更新,关注引用的增加,把漏标和错标的 垃圾对象黑色重新变为灰色, 把指向的对象 标出不是垃圾
2.SATB snapshot at the begginning(b1算法)
关注在 删除时, 把删除的引用的指向放到栈,
下次清理垃圾时,把引用拿出来,然后继续扫描