对象之死

1. 判断对象是否可以进行回收

1.1 引用计数算法

  定义 : 为对象添加一个引用计数器, 每当有一个地方引用它,计数器值就加一, 当引用失效时, 计数器值就减一.

  优点 : 实现简单, 效率高

  缺点 : 很难解决对象之间相互循环引用的问题

1.2 可达性分析算法

  基本思想 : 通过一系列称为"GC Roots"的对象作为起始点, 从这些节点向下搜索, 搜索走过的路径称为引用链, 当一个对象到GC Roots 没有任何引用链相连时, 则此对象是不可用的.

  GC Roots :

  1. 虚拟机栈(栈帧中的本地变量表)中引用的对象
  2. 方法区中静态属性引用的对象
  3. 方法区中常量引用的对象
  4. 本地方法栈中JNI(Native方法)引用的对象

  引用类型 : 

  1. 強引用 : 类似于 Object obj = new Object() 的这类引用, GC不会回收强引用引用的对象
  2. 软引用 : 描述一些还有用但是非必需的对象, 在系统发生内存溢出异常之前, 会把这些对象列进回收范围进行二次回收. SoftReference类来实现软引用
  3. 弱引用 : 描述非必需对象. 此类对象只能生存到下一次垃圾回收之前. 垃圾回收时, 无论当前内存是否足够, 都会回收掉只被弱引用关联的对象. WeakReference类实现弱引用
  4. 虚引用 : 唯一目的是在对象被回收时收到一个系统通知.

1.3 对象的回收

  当对象可达性分析后为被判断为回收对象时, 会进行第一次标记, 并判断此对象有无必要执行finalize().

    没有必要:

      a. 对象未覆盖finalize()

      b. 虚拟机已经调用过finalize()

    有必要 : 

      对象被放置在F-Quene队列中, 稍后虚拟机自动建立低优先级的Finalizer线程去执行它的finalize()(并不承诺等待他运行结束,可能发生死循环), 稍后对队列中的对象进行第二次小规模的标记, 之后就会被真正回收.

      对象可在finalize()中拯救自己, 重新与引用链上的对象建立关联

    任何对象的finalize()只会被系统调用一次

2. 回收方法区

  主要回收废弃的常量和无用的类.

2.1 废弃的常量

  1. 没有任何地方引用该常量时即可回收它.

2.2 无用的类

  1. 该类的所有实例都已经被回收, Java堆中不存在任何该类的实例
  2. 加载该类的ClassLoder已经被回收
  3. 该类的Class对象没有在任何地方被引用, 无法在任何地方通过反射访问该类的方法
原文地址:https://www.cnblogs.com/virgosnail/p/9509884.html