JVM---对象是否存活及被引用的状态

news2024/11/15 19:50:03

1.如何判断对象是否存活

1.1 引用计数算法

        概念:在对象头部增加一个引用计数器,每当有一个地方引用它时,计数器值就加一;当引用失效时,计数器值就减一;任何时刻计数器为零的对象就是不可能再被使用的。

        优点:速度快,高效

        缺点: 假如此时A引用B,B引用A那么,计数永远不为0,那么永远无法回收他们

1.2 可达性分析算法:

        概念:通过一系列称为“GC Roots”的根对象作为起始节点集,从这些节点开始,根据引用关系向下搜索,搜索过程所走过的路径称为“引用链”(Reference Chain),如果某个对象到GC Roots间没有任何引用链相连,或者用图论的话来说就是从GC Roots到这个对象不可达时,则证明此对象是不可能再被使用的。

       总结概念: 也就是找到是否连接根节点,此时如果A引用B,B引用A就不会发生,循环回收不掉的问题,因为他们找不到连接的根节点,也是当前主流的判断对象是否存活的算法

        注意:即使在可达性分析算法中判定为不可达的对象,也不是“非死不可”的,这时候它们暂时还处于“缓刑”阶段,要真正宣告一个对象死亡,至少要经历两次标记过程:如果对象在进行可达性分析后发现没有与GC Roots相连接的引用链,那它将会被第一次标记,随后进行一次筛选,筛选的条件是此对象是否有必要执行finalize()方法。

2.再谈引用

        无论是通过引用计数算法判断对象的引用数量,还是通过可达性分析算法判断对象是否引用链可 达,判定对象是否存活都和“ 引用 离不开关系。
        在JDK 1.2 版之前, Java 里面的引用是很传统的定义: 如果reference 类型的数据中存储的数值代表的是另外一块内存的起始地址,就称该 reference 数据是代表 某块内存、某个对象的引用。这种定义并没有什么不对,只是现在看来有些过于狭隘了,一个对象在 这种定义下只有“ 被引用 或者 未被引用 两种状态,对于描述一些 食之无味,弃之可惜 的对象就显 得无能为力。
        譬如我们希望能描述一类对象:当内存空间还足够时,能保留在内存之中,如果内存空
间在进行垃圾收集后仍然非常紧张,那就可以抛弃这些对象 —— 很多系统的缓存功能都符合这样的应用场景。
        所以在JDK 1.2版之后,Java对引用的概念进行了扩充,引入了四种引用

3.四种引用

2.1  强引用

        是最传统的“引用”的定义,是指在程序代码之中普遍存在的引用赋值,即类似“Object obj=new Object()”这种引用关系。无论任何情况下,只要强引用关系还存在,垃圾收集器就永远不会回收掉被引用的对象。

2.2 软引用

        是用来描述一些还有用,但非必须的对象。只被软引用关联着的对象,在系统将要发生内存溢出异常前,会把这些对象列进回收范围之中进行第二次回收,如果这次回收还没有足够的内存,才会抛出内存溢出异常。在JDK 1.2版之后提供了SoftReference类来实现软引用。

2.3 弱引用

        也是用来描述那些非必须对象,但是它的强度比软引用更弱一些,被弱引用关联的对象只能生存到下一次垃圾收集发生为止。当垃圾收集器开始工作,无论当前内存是否足够,都会回收掉只被弱引用关联的对象。在JDK 1.2版之后提供了WeakReference类来实现弱引用。

2.4 虚引用

        也称为“幽灵引用”或者“幻影引用”,它是最弱的一种引用关系。一个对象是否有虚引用的存在,完全不会对其生存时间构成影响,也无法通过虚引用来取得一个对象实例。为一个对象设置虚引用关联的唯一目的只是为了能在这个对象被收集器回收时收到一个系统通知。在JDK 1.2版之后提供了PhantomReference类来实现虚引用。

3. 软引用的进一步了解

3.1 软引用的使用场景

         软引用主要用于实现内存敏感的高速缓存。当系统内存充足时,软引用的对象可以长时间驻留在内存中,供程序快速访问;当系统内存不足时,这些对象可以被垃圾回收器回收,从而避免内存溢出错误。这种机制非常适合用于缓存系统,如图片缓存、页面缓存等。

3.2 为什么用到了软引用

  1. 内存压力下的灵活应对:软引用允许JVM在内存紧张时自动回收对象,从而避免了程序因为内存不足而崩溃的风险。

  2. 提高性能:通过保留软引用对象,在内存充足时可以直接访问这些对象,减少了重新加载或重新计算这些对象所需的时间和资源。

  3. 资源管理的灵活性:开发者可以通过软引用来控制缓存的大小和生命周期,而不是完全依赖于JVM的垃圾回收机制。

3.3 软引用的使用(小例子)

import java.lang.ref.SoftReference;  
  
public class SoftReferenceExample {  
    public static void main(String[] args) {  
        // 假设这是我们需要缓存的数据  
        Object data = new Object();  
  
        // 创建一个软引用指向这个数据  
        SoftReference<Object> softRef = new SoftReference<>(data);  
  
        // 使用softRef.get()来获取软引用指向的对象  
        Object cachedData = softRef.get();  
  
        // 模拟内存紧张的情况(实际上在简单示例中无法直接模拟)  
        // 在实际环境中,当JVM进行垃圾回收时,如果内存不足,可能会回收softRef指向的对象  
  
        // 再次尝试获取对象,如果对象已被回收,则返回null  
        cachedData = softRef.get();  
        if (cachedData != null) {  
            // 对象仍然存在,可以继续使用  
        } else {  
            // 对象已被回收,需要重新加载或重新计算  
        }  
    }  
}

注意:由于垃圾回收的时机和过程是由JVM的垃圾回收器控制的,因此我们不能精确地预测软引用对象何时会被回收。在实际应用中,开发者需要根据应用的内存需求和性能要求来合理使用软引用。

4. 弱引用的进一步了解

4.1 使用场景

  1. 缓存系统
    • 在一些缓存系统中,特别是当缓存的数据量很大且不是必需时,可以使用弱引用来引用这些数据。这样,当JVM内存不足时,这些数据可以被自动回收,从而避免内存溢出。
    • 例如,WeakHashMap就是基于弱引用实现的,它允许键值对中的键是弱引用的。这意味着,如果某个键除了被WeakHashMap所引用外,没有其他强引用指向它,那么这个键以及它所对应的值都可能被垃圾回收器回收。
  2. 生命周期较短的临时对象
    • 对于那些生命周期较短,且对内存敏感的临时对象,可以使用弱引用来引用它们。这样,一旦这些对象不再被其他强引用所指向,它们就可以被垃圾回收器及时回收。

4.2 为什么用到了弱引用

  1. 内存管理的灵活性
    • 弱引用提供了一种比软引用更加灵活的内存管理方式。通过弱引用,开发者可以更加精确地控制对象的生命周期,避免内存泄漏,同时也能够确保在内存不足时能够自动回收非必需的对象。
  2. 减少内存泄漏的风险
    • 在一些复杂的应用程序中,由于对象之间的引用关系错综复杂,很容易出现内存泄漏的情况。通过使用弱引用,可以减少因为对象之间的强引用关系而导致的内存泄漏风险。
  3. 提升性能
    • 在一些性能敏感的应用程序中,及时回收不再使用的对象可以释放更多的内存空间,从而提升应用程序的性能。弱引用通过自动回收非必需的对象,有助于减少内存占用,提升性能。

4.3 弱引用的使用(小例子)

import java.lang.ref.WeakReference;  
  
public class WeakReferenceExample {  
    public static void main(String[] args) {  
        // 创建一个强引用对象  
        Object strongRef = new Object();  
  
        // 创建一个弱引用对象,指向强引用对象  
        WeakReference<Object> weakRef = new WeakReference<>(strongRef);  
  
        // 验证弱引用是否有效  
        System.out.println(weakRef.get()); // 输出对象地址  
  
        // 将强引用置为null,模拟对象不再被强引用  
        strongRef = null;  
  
        // 触发垃圾回收(注意:实际环境中,垃圾回收的时机是不确定的)  
        System.gc();  
  
        // 再次验证弱引用是否有效  
        // 由于强引用已被置为null,且没有其他强引用指向该对象,因此该对象可能会被垃圾回收  
        // 此时,weakRef.get()可能返回null  
        System.out.println(weakRef.get()); // 可能输出null  
    }  
}

同样和弱引用相同:由于垃圾回收的时机和过程是由JVM的垃圾回收器控制的,因此我们不能精确地预测弱引用对象何时会被回收。在实际应用中,开发者需要根据应用的内存需求和性能要求来合理使用弱引用。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.coloradmin.cn/o/1932094.html

如若内容造成侵权/违法违规/事实不符,请联系多彩编程网进行投诉反馈,一经查实,立即删除!

相关文章

喰星云·数字化餐饮服务系统 多处 SQL注入漏洞复现

0x01 产品简介 喰星云数字化餐饮服务系统是一款专为餐饮企业设计的综合性管理软件,旨在通过信息化手段提升餐饮企业的运营效率、降低运营成本,并实现数据驱动的决策管理。该系统包括供应链管理、财务管理、巡店管理、人力资源管理等多个模块,可全面覆盖餐饮企业的日常运营需…

【多线程综合】java何时考虑线程安全问题、怎么考虑、又怎么解决?

前言&#xff1a;在编程中&#xff0c;线程安全是一个非常重要的概念。它涉及到多个线程并发访问共享资源时的正确性和一致性。在Java中&#xff0c;为了确保线程安全&#xff0c;我们需要考虑一些关键因素。 1、什么是线程安全 线程安全是指当多个线程同时访问一个对象时&am…

十大排序 之 快速排序

&#xff01;&#xff01;&#xff01;排序仅针对于数组哦本次排序是按照升序来的哦代码后边有图解哦 介绍 快速排序英文名为Quick Sort 基本思路 快速排序采用的是分治思想&#xff0c;即在一个无序的序列中选取一个任意的基准元素base&#xff0c;利用base将待排序的序列分…

基于RK3588的8K视频解码显示案例分享!引领超高清工业视频时代

8K、4K、2K显示对比 2K分辨率&#xff1a;也称为全高清&#xff08;FULL HD&#xff09;&#xff0c;它具有1920 x 1080像素的分辨率。这是目前大多数消费者电视和电脑显示器的标准分辨率&#xff0c;可以提供良好的图像质量。 4K分辨率&#xff1a;也称为4K超高清&#xff0…

我无法给博客园出钱,那我就出点建议吧

相信这张图大家都已经看见过了&#xff0c;从去年就传出博客园经营困难的情况&#xff0c;其实很多平台&#xff0c;不止是博客园&#xff0c;包括现在国内的很多公司都一样&#xff0c;经营是一件大难题&#xff0c;但很多公司我们不知道&#xff0c;悄无声息的倒下了。而博客…

【雅思备考IELTS】写作第一部分Writing Part One

Tips for IELTS Writing (Part 1) By James Lee 2024/7/15 Part 1: 图表数据分析 Analysis of a Graph / Chart / Curve, etc. 这部分一般是让分析一张图表&#xff08;Graph或Chart&#xff09;&#xff0c;用时约20分钟&#xff0c;字数不用太多&#xff0c;150词以上即可。…

推荐一个可以体验正版ChatGPT的平台

在鱼龙混杂的API市场&#xff0c;智创聚合API以其卓越的性能和创新的服务理念&#xff0c;为用户带来了前所未有的体验。我们自豪地宣布&#xff0c;现在加入我们的限时官方API渠道&#xff0c;您将享受到更快速率提升&#xff0c;以及更高质量的回复服务&#xff0c;而这些仅需…

Python酷库之旅-第三方库Pandas(028)

目录 一、用法精讲 71、pandas.tseries.api.guess_datetime_format函数 71-1、语法 71-2、参数 71-3、功能 71-4、返回值 71-5、说明 71-6、用法 71-6-1、数据准备 71-6-2、代码示例 71-6-3、结果输出 72、pandas.util.hash_array函数 72-1、语法 72-2、参数 72…

【PostgreSQL】PostgreSQL简史

博主介绍&#xff1a;✌全网粉丝20W&#xff0c;CSDN博客专家、Java领域优质创作者&#xff0c;掘金/华为云/阿里云/InfoQ等平台优质作者、专注于Java技术领域✌ 技术范围&#xff1a;SpringBoot、SpringCloud、Vue、SSM、HTML、Nodejs、Python、MySQL、PostgreSQL、大数据、物…

Java SHA-256哈希算法

一、SHA-256算法简介 SHA-2&#xff08;Secure Hash Algorithm 2&#xff09;&#xff0c;一种散列函数算法标准&#xff0c;由美国国家安全局研发&#xff0c;由美国国家标准与技术研究院&#xff08;NIST&#xff09;在2001年发布&#xff0c;属于SHA算法之一&#xff0c;是…

C++ std::lock_guard和 std::unique_lock

二者都是 C 标准库中用于管理互斥锁&#xff08;mutex&#xff09;的 RAII&#xff08;Resource Acquisition Is Initialization&#xff09;机制的类。这些类可以确保互斥锁在构造时被获取&#xff0c;在析构时被释放&#xff0c;从而避免死锁和资源泄漏问题。不过&#xff0c…

使用windows批量解压和布局ImageNet ISLVRC2012数据集

使用的系统是windows&#xff0c;找到的解压命令很多都linux系统中的&#xff0c;为了能在windows系统下使用&#xff0c;因此下载Git这个软件&#xff0c;在其中的Git Bash中使用以下命令&#xff0c;因为Git Bash集成了很多linux的命令&#xff0c;方便我们的使用。 ImageNe…

【博士每天一篇文献-算法】 PNN网络启发的神经网络结构搜索算法Progressive neural architecture search

阅读时间&#xff1a;2023-12-23 1 介绍 年份&#xff1a;2018 &#xff1a;Chenxi Liu,Google DeepMind研究科学家;Barret Zoph,OpenAI;Maxim Neumann,Goolge 会议&#xff1a;B区会议&#xff0c; Proceedings of the European conference on computer vision (ECCV). 引用…

【Android14 ShellTransitions】(七)Transition就绪

Transition.onTransactionReady的内容比较长&#xff0c;我们挑重点的部分逐段分析&#xff08;跳过的地方并非不重要&#xff0c;而是我柿子挑软的捏&#xff09;。 1 窗口绘制状态的流转以及显示SurfaceControl 注意我们这里的SurfaceControl特指的是WindowSurfaceControll…

Excel办公技巧:制作二级联动下拉菜单

分享制作二级联动下拉菜单的方法&#xff0c;即使数据有增删&#xff0c;菜单也能自动更新&#xff01; 可以通过先定义名称&#xff0c;再结合数据验证&#xff0c;来做二级联动下拉菜单。 1. 准备数据 首先&#xff0c;我们需要准备好要进行二级联动下拉菜单的数据&#xff…

K8S 上部署 Emqx

文章目录 安装方式一&#xff1a;快速部署安装方式二&#xff1a;定制化部署1. 使用 Pod 直接部署 EMQX Broker2. 使用 Deoloyment 部署 Pod3. 使用 Services 公开 EMQX Broker Pod 服务4. 通过 kubernetes 自动集群 EMQX MQTT 服务器5. 修改 EMQX Broker 的配置6. 赋予 Pod 访…

共享自助台球厅系统,扫码开台,物联网开灯,智能计费

共享自助台球厅系统&#xff0c;扫码开台&#xff0c;物联网开灯&#xff0c;智能计费 含小程序&#xff0c;商家手机端和pc管理端 后端php 前端uniapp 纯开源 可定制 持续更新

常用的点云预处理算法

点云预处理是处理点云数据时的重要部分&#xff0c;其目的是提高点云数据的质量和处理效率。通过去除离群点、减少点云密度和增强特征&#xff0c;可以消除噪声、减少计算量、提高算法的准确性和鲁棒性&#xff0c;从而为后续的点云处理和分析步骤&#xff08;如配准、分割和重…

实战打靶集锦-31-monitoring

文章目录 1. 主机发现2. 端口扫描3. 服务枚举4. 服务探查4.1 ssh服务4.2 smtp服务4.3 http/https服务 5. 系统提权5.1 枚举系统信息5.2 枚举passwd文件5.3 枚举定时任务5.4 linpeas提权 6. 获取flag 靶机地址&#xff1a;https://download.vulnhub.com/monitoring/Monitoring.o…

算法力扣刷题记录 四十九【112. 路径总和】和【113. 路径总和ii】

前言 二叉树篇继续。 记录 四十九【112. 路径总和】和【113. 路径总和ii】 一、【112. 路径总和】题目阅读 给你二叉树的根节点 root 和一个表示目标和的整数 targetSum 。判断该树中是否存在 根节点到叶子节点 的路径&#xff0c;这条路径上所有节点值相加等于目标和 target…