• JVM(2)


    垃圾回收

    如果判断对象可以回收

    引用计数法

    • 当一个对象被引用时,就使引用对象的值加一,当值为 0 时,就表示该对象不被引用,可以被垃圾收集器回收。
    • 这个引用计数法听起来不错,但是有一个弊端,如下图所示,循环引用时,两个对象的计数都为1,导致两个对象都无法被释放。
      在这里插入图片描述

    可达性分析算法

    1. JVM 中的垃圾回收器通过可达性分析来探索所有存活的对象
    2. 扫描堆中的对象,看能否沿着 GC Root 对象为起点的引用链找到该对象,如果找不到,则表示可以回收
    3. 可以作为 GC Root 的对象:
      1.虚拟机栈(栈帧中的本地变量表)中引用的对象。
      2.方法区中类静态属性引用的对象
      3.本地方法栈中 JNI(即一般说的Native方法)引用的对象

    四种引用在这里插入图片描述

    1. 强引用
      只有所有 GC Roots 对象都不通过【强引用】引用该对象,该对象才能被垃圾回收
    2. 软引用(SoftReference)
      仅有软引用引用该对象时,在垃圾回收后,内存仍不足时会再次触发垃圾回收,回收软引用对象
      >可以配合引用队列来释放软引用自身
    3. 弱引用(WeakReference)
      仅有弱引用引用该对象时,在垃圾回收时,无论内存是否充足,都会回收弱引用对象
      >可以配合引用队列来释放弱引用自身
    4. 虚引用(PhantomReference)
      必须配合引用队列使用,主要配合 ByteBuffer 使用,被引用对象回收时,会将虚引用入队,
      >由 Reference Handler 线程调用虚引用相关方法释放直接内存
    5. 终结器引用(FinalReference)
      无需手动编码,但其内部配合引用队列使用,在垃圾回收时,终结器引用入队(被引用对象暂时没有被回收),再由 Finalizer 线程通过终结器引用找到被引用对象并调用它的 finalize 方法,第二次 GC 时才能回收被引用对象。

    垃圾回收算法

    1. 标记清除
    2. 标记整理(标记压缩)
    3. 复制

    标记清除

    首先标记出所有需要回收的对象,在标记完成后统一回收掉所有的被标记对象。

    标记和清除的效率都不高。
    会产生内存碎片

    在这里插入图片描述

    标记整理

    先标记出要被回收的对象,然后让所有存活的对象都向一端移动,然后直接清理掉边界以外的内存。解决了复制算法和标记清理算法的问题。

    没有内存碎片

    在这里插入图片描述

    复制

    将可用内存按容量划分为大小相等的两块,每次只使用其中的一块,当这一块内存用完了,就将还存活的对象复制到另外一块上面,然后再把已使用过的内存空间一次清理掉。

    不会有内存碎片
    需要占用两倍内存空间

    在这里插入图片描述

  • 相关阅读:
    NER中BiLSTM-CRF解读Forward_algorithm
    技术开创、优势沉淀|高通平台解决方案生态系统(PSE)计划,诚邀合作伙伴加入!
    37. 干货系列从零用Rust编写负载均衡及代理,负载均衡中try_files实现
    学习FPGA之五:工具链
    【机器学习】sklearn降维算法PCA
    内核查找符号指针函数kallsyms_lookup_name
    【小5聊】C#控制台使用RabbitMQ进行简单的消息生产和消费
    [极客大挑战 2019]BuyFlag 1(两种解法)
    rust编程-rust所有权理解(chapter 4.2 引用实质是借用)
    java集合类史上最细讲解 - Collections工具类
  • 原文地址:https://blog.csdn.net/qq_56851614/article/details/126487408