jvm-GC

一、判断可回收对象的算法

1、引用计数法

  每个对象配一个引用计数器,被引用一次就+1,引用失效就-1,为0则对象可回收

  好处:简单高效

  坏处:解决不了循环引用的垃圾对象

2、可达性分析算法

  即是否从“GC ROOT”的引用路径可达,不可达的对象就是垃圾了

  GC ROOT:

  • 本地变量表中引用的对象
  • 方法区中静态变量引用的对象
  • 方法区中常量引用的对象
  • Native方法引用的对象

二、四种引用

  1、强引用:被引用的对象永远不会被回收(即程序代码中直接的引用)

  2、软引用:内存不够时就将相关对象回收掉(提供了SoftReference类来实现软引用)

  3、弱引用、虚引用。。。略

三、finalize()  

  对象逃离被回收的最后方法,只能使用一次

四、回收方法区(回收常量和类)

  可被回收的类:没有实例存在,对应的ClassLoader被回收,java.lang.Class没有被引用。

五、垃圾收集算法

  1、标记-清除算法

    标记垃圾完成后,统一清除

    缺点:1,效率低  2,有空间碎片

  2、复制算法

    把一块内存分成两块,当其中的一块用完后,将还存活的对象移到另一块上,然后用完的那个块全部清空。

    缺点:内存变为了原来的一半

    新生代采用的是复制算法,因为对象的存活率很低,将内存分为1个Eden区和两个Survivor区,比例为8:1:1,每次使用Eden区和一块Survivor区,回收时,将存活的对象复制到另一个Survivor区中。

    (当Survivor区中的内存不够用时,则通过分配担保机制进入老年代

  3、标记整理算法

    即先标记,然后存活的对象向一端移动,紧凑起来,再将端边界以外的内存清空。

六、具体实现

  1、枚举根节点

  遍历寻找引用很费时,有一组叫OopMap的数据结构可以知道哪些位置有着引用。

  2、安全点

  执行GC的时间点。

  当发生GC时,不直接对线程进行中断操作,而是简单的设置一个中断标志,每个线程运行到Safe Point的时候,主动去轮询这个中断标志,如果中断标志为真,则将自己进行中断挂起。

  这里忽略了一个问题,当发生GC时,运行中的线程可以跑到Safe Point后进行挂起,而那些处于Sleep或Blocked状态的线程在此时无法响应JVM的中断请求,无法到Safe Point处进行挂起,针对这种情况,可以使用安全区域(Safe Region)进行解决。

  3、安全区域

  Safe Region是指在一段代码片段中,对象的引用关系不会发生变化,在这个区域中的任何位置开始GC都是安全的。
  1、当线程运行到Safe Region的代码时,首先标识已经进入了Safe Region,如果这段时间内发生GC,JVM会忽略标识为Safe Region状态的线程;
  2、当线程即将离开Safe Region时,会检查JVM是否已经完成GC,如果完成了,则继续运行,否则线程必须等待直到收到可以安全离开Safe Region的信号为止;

七、垃圾收集器

  参考:http://www.importnew.com/23640.html

八、内存分配与回收策略

  待续

posted @ 2019-03-07 20:23  hzhuan  阅读(119)  评论(0编辑  收藏  举报