深入理解Java虚拟机笔记---判断对象是否存活

博途 V15.1安装步骤 温馨提醒:安装此软件电脑配置至少应满足以下要求 处理器 CoreTM i5-3320M 3.3 GHz 或相当 内存 至少8G 硬盘 300 GB SSD 显示器 15.6' 宽屏显示 (1920 x 1080) 1.双击打开【Siemens v15.1】文件夹。 2.鼠标右击【STEP 7 BasicProfess... 阅读详情

堆中几乎存放着Java世界中所有的对象实例,垃圾收集器在对堆回收之前,第一件事情就是要确定这些对象哪些还“存活”着,哪些对象已经“死去”(即不可能再被任何途径使用的对象)

1.引用计数算法

很多教科书判断对象是否存活的算法是这样的:给对象中添加一个引用计数器,每当有一个地方引用它时,计数器值加1;当引用失效时,计数器减1;任何时刻计数器都为0的对象就是不可能再被使用的。

引用计数算法(Reference Counting)的实现简单,判断效率也很高,在大部分情况下它都是一个不错的算法。但是Java语言中没有选用引用计数算法来管理内存,其中最主要的一个原因是它很难解决对象之间相互循环引用的问题。

例如:在testGC()方法中,对象objA和objB都有字段instance,赋值令objA.instance=objB及objB.instance=objA,除此之外这两个对象再无任何引用,实际上这两个对象都已经不能再被访问,但是它们因为相互引用着对象方,异常它们的引用计数都不为0,于是引用计数算法无法通知GC收集器回收它们。

public class ReferenceCountingGC {
    public Object instance = null;
    private static final int _1MB = 1024 *1024;
    /**
     * 只是为了占点内存
     */
    private byte[] bigSize = new byte[2 * _1MB];

<span class="hljs-function"><span class="hljs-keyword">public</span> <span class="hljs-keyword">static</span> <span class="hljs-keyword">void</span> <span class="hljs-title">main</span>(<span class="hljs-params">String[] args</span>) </span>{
    ReferenceCountingGC objA = <span class="hljs-keyword">new</span> ReferenceCountingGC();
    ReferenceCountingGC objB = <span class="hljs-keyword">new</span> ReferenceCountingGC();
    objA.instance = objB;
    objB.instance = objA;

    objA = <span class="hljs-literal">null</span>;
    objB = <span class="hljs-literal">null</span>;

    <span class="hljs-comment">//假设在这里发生GC,那么objA与objB是否会被回收</span>
    System.gc();

}
复制代码

运行结果为:

[GC [DefNew: 234K->64K(960K), 0.0009447 secs][Tenured: 2125K->2189K(4096K), 0.0048757 secs] 2282K->2189K(5056K), [Perm : 365K->365K(12288K)], 0.0058659 secs] [Times: user=0.00 sys=0.00, real=0.00 secs]
[Full GC (System) [Tenured: 4237K->141K(6148K), 0.0052656 secs] 4237K->141K(7108K), [Perm : 365K->365K(12288K)], 0.0052973 secs] [Times: user=0.01 sys=0.00, real=0.01 secs]
Heap
 def new generation   total 960K, used 18K [0x23b10000, 0x23c10000, 0x23ff0000)
  eden space 896K,   2% used [0x23b10000, 0x23b14818, 0x23bf0000)
  from space 64K,   0% used [0x23c00000, 0x23c00000, 0x23c10000)
  to   space 64K,   0% used [0x23bf0000, 0x23bf0000, 0x23c00000)
 tenured generation   total 6148K, used 141K [0x23ff0000, 0x245f1000, 0x27b10000)
   the space 6148K,   2% used [0x23ff0000, 0x240136b8, 0x24013800, 0x245f1000)
 compacting perm gen  total 12288K, used 365K [0x27b10000, 0x28710000, 0x2bb10000)
   the space 12288K,   2% used [0x27b10000, 0x27b6b578, 0x27b6b600, 0x28710000)
    ro space 8192K,  63% used [0x2bb10000, 0x2c023b48, 0x2c023c00, 0x2c310000)
    rw space 12288K,  53% used [0x2c310000, 0x2c977f38, 0x2c978000, 0x2cf10000)

复制代码

在运行结果中可以看到GC日志中包含"4237K->141K",老年代从4273K(大约4M,其实就是objA与objB)变为了141K,意味着虚拟并没有因为这两个对象相互引用就不回收它们,这也证明虚拟并不是通过通过引用计数算法来判断对象是否存活的。大家可以看到对象进入了老年代,但是大家都知道,对象刚创建的时候是分配在新生代中的,要进入老年代默认年龄要到了15才行,但这里objA与objB却进入了老年代。这是因为Java堆区会动态增长,刚开始时堆区较小,对象进入老年代还有一规则,当Survior空间中同一代的对象大小之和超过Survior空间的一半时,对象将直接进行老年代。

2.根搜算法

在主流的商用程序语言中(Java和C#),都是使用根搜索算法(GC Roots Tracing)判断对象是否存活的。这个算法的基本思路就是通过一系列名为"GC Roots"的对象作为起始点,从这些节点开始向下搜索,搜索所走过的路径称为引用链(Reference Chain),当一个对象到GC Roots没有任何引用链相连时,则证明此对象是不可用的,如下图:

file

对象bject5, object6, object7虽然有互相判断,但它们到GC Roots是不可达的,所以它们将会判定为是可回收对象。 在Java语言里,可作为GC Roots对象的包括如下几种:

  • 虚拟机栈(栈桢中的本地变量表)中的引用的对象
  • 方法区中的类静态属性引用的对象
  • 方法区中的常量引用的对象
  • 本地方法栈中JNI的引用的对象


作者:大盛玩java
链接:https://juejin.cn/post/7005461387535187976
来源:掘金
著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。

【Unity 城市建模插件】POLY-Megapolis City Pack 提供超过数百种城市建筑、道路、车辆与城市家具模型,完美适用于构建现代化城市、模拟城市游戏、都市题材冒险类游戏和开放世界项目 POLY - Megapolis City Pack 是一套风格统一、内容丰富的低多边形城市建模资源包,专为 Unity 引擎设计。该资源包提供超过数百种城市建筑、道路、车辆与城市家具模型,完美适用于构建现代化城市、模拟城市游戏、都市题材冒险类游戏和开放世界项目。无论是快速原型开发还是正式发布项目,POLY 系列都能提供高效、风格统一的解决方案。 阅读详情

相关推荐

基于SECS协议开发的简明教程(1)

SEMI SECS MES E4 E5 E30 E37 HSMS SDK

L251210269的专栏 7632

JVM:判断对象是否存活

JVM如何判断对象是否存活

Java开发相关的学习笔记 1218

uniapp [安卓苹果App端] - 实现获取手机日历读写权限+调用本机日历数据及操作功能+日历中插入事项事件提醒,检测权限手机日历权限是否开启并引导用户同意授权,uniApp app端开启日历授权

uni-app,权限,手机日历权限,安卓Android,苹果ios,uniapp安卓android获取本机日历读写权限使用,uni-app获取日历权限并实现插入事项事件功能 uniapp苹果IOS系统不支持怎么办,判断权限,权限被拒绝了怎么办,获取日历权限报错,读取日历数据农历阴历并操作插入移除,给用户手机日历中放入一条提示,UniApp调用日历进行读写,打包上架后如何获取,安卓ios权限检测,安卓和ios权限获取,uniapp的APP端日历读写权限与使用示例代码,如何开启日历权限,日历的新增事项和删除,判

🏆 前端领域优质创作者 1万+

JVM中判断对象的存活

判断对象是否存活的方法 引用计数法 可达性分析 一、引用计数法 在对象中添加一个引用计数器,每当有一个地方引用该对象,计数器就+1,当引用失效时,计数器-1 存在的问题 两个对象相互引用的时候可能无法被回收 二、可达性分析(JVM中使用的方法) 通过一系列被称为GC Roots的对象作为起始点,从这些节点开始向下搜索,搜索所走过的路径称为引用链,当一个对象到GC Roots没有任何引用链相连时,说明此对象是不可用的 JVM中作为GC Roots的对象 虚拟机栈(栈帧中的局部变量表)中

weixin_42779514的博客 300

备战数学建模38-粒子群算法pso番外篇1(攻坚战2)

粒子群算法最初是根据鸟类群体行为得到的启发,对鸟群行为进行仿真的算法,是一种启发式算法,也就是智能优化算法,利用信息共享,通过中间信息进行改进搜索,从而获得问题的可行解。我们简单从下图去体会一下粒子群算法,就是有多个鸟,每个鸟相当于一个粒子,每只鸟的位置受自己认知的历史最佳位置和当前距离食物最近的鸟的位置的影响。我们进一步分析这个图,可以得到两个公式,第一个是速度公式,即每只鸟的当前速度受上一步的速度惯性,自我认知和社会认知三部分影响,第二个是位置公式,即每只鸟的位置受上一位置和上一位置的速度的影响。

nuist_NJUPT的博客 1666

Open3D 球旋转算法(BPA)三维建模【2026最新版】

球旋转算法,博客长期更新,本文最新更新时间为:2026年4月11日。

点云侠的博客 37万+

JVM判断对象是否存活

堆中几乎存放着所有的对象实例,垃圾收集器在对堆回收之前,第一件事情就是要确定这些对象哪些还“存活”,那些对象已经“死去”(即不可能被任何途径使用的对象) 一、引用计数算法(Reference Counting) 给对象中添加一个引用计数器,每当又一个地方引用它时,计数器值加1;当引用失效时,计数器减1;任何时刻计数器都为0的对象就是不可能在被使用的.但是Java语言中没有选用引用计数法来管理内...

weixin_34375233的博客 292

ros系统在Debian系统上的移植

摘要:本文详细介绍了在Debian系统上移植ROS(机器人操作系统)的完整流程。主要内容包括:1)Debian版本与ROS版本的对应关系;2)配置软件源和安装依赖的具体命令;3)安装ROS核心组件和开发工具的步骤;4)常见兼容性问题的解决方案;5)性能优化和维护建议。重点强调了版本匹配的重要性,推荐选择LTS版本组合(如Debian11+ROS Noetic),并提供了从基本安装到自定义功能包编译的全套方案。文中包含详细的终端命令,可帮助用户顺利完成ROS移植并解决可能遇到的问题。

start_up_go的博客 1494

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

无论是通过引用计数算法判断对象的引用数量,还是通过可达性分析算法判断对象是否引用链可 达,判定对象是否存活都和“引用离不开关系。在JDK 1.2版之前,Java里面的引用是很传统的定义: 如果reference类型的数据中存储的数值代表的是另外一块内存的起始地址,就称该reference数据是代表 某块内存、某个对象的引用。这种定义并没有什么不对,只是现在看来有些过于狭隘了,一个对象在 这种定义下只有“被引用或者未被引用两种状态,对于描述一些食之无味,弃之可惜。

你我约定有三的博客 1426

Python爬虫实战:使用最新技术爬取新浪新闻首页数据

本文详细介绍了三种爬取新浪新闻首页的技术方案,从简单的requests-html到强大的Playwright,再到分布式Scrapy架构。小规模爬取:requests-html或aiohttp方案需要JavaScript渲染:Playwright方案大规模分布式爬取:Scrapy-Redis方案。

2201_76125261的博客 1244

ParaView: GUI 轴网格

ParaView: GUI 轴网格

希望我的博客,能帮上你解决学习中工作中所遇到的问题 1924

JVM判定对象是否存活

文章目录确定对象是否存活算法1、引用技术算法2、可达性分析算法JDK引用 确定对象是否存活算法 1、引用技术算法 给对象中添加一个引用计数器,每当一个地方引用它时,计数器值就+1;当引用失效时,计数器值就-1;任何时刻计数器为0的对象就是不可能再被使用的。 优点:实现简单,判定效率高 缺点:很难解决对象相互循环引用问题 public class ReferenceCountingGc{ p...

白杨 485

多智能体系统在AI物流优化中的实际应用案例

订单波峰波谷难应对(如双11订单量暴增300%);动态干扰难处理(如突发交通拥堵、客户临时改地址);全局优化难实现(单辆车最优≠整体最优)。本文聚焦“多智能体系统(MAS)”这一AI技术,讲解其如何通过“群体智能”破解物流调度难题,并结合实际案例展示落地效果。本文从“生活故事→核心概念→技术原理→实战案例→未来趋势”逐步展开,用“快递员团队协作送外卖”类比MAS运作,结合Python代码模拟任务分配,最后通过某物流企业的真实项目验证效果。

AIGC应用创新大全的博客 1632

《深入理解Java虚拟机》读书笔记:判断对象是否存活

本节内容的概要如下;对象已死吗?

Gefangenes的博客 114

文档:亲测可用解决vnc灰屏,黑屏,鼠标大黑叉情况

主要解决vnc-viewer灰屏,黑屏,鼠标大黑叉等现象,详细见文档。

LinePhone3.2.7(android端最新版本) sip客户端

SIP客户端For android:LinePhone3.2.7(最新版本),官网地址:http://www.linphone.org/

深入理解java虚拟机学习笔记(4)——判断对象是否存活

判断对象是否存活 程序计数器,虚拟机栈,本地方方法栈这几个区域的内存分配和回收都具备确定性,当线程结束时,内存自然就跟着回收了。 Java堆和方法区这两个区域只有处于运行期,才能知道程序会创建哪些对象,创建多少对象,这部分内存的分配和回收是动态的。 目录判断对象是否存活一、引用计数算法二、可达性分析算法二、 一、引用计数算法 示例:111 二、可达性分析算法 二、 ...

pushen3584的博客 189

数学建模模型总结

这是本人在两年内准备参加数学建模竞赛搜集到的模型资料,已经经过了本人的筛选和整理,希望能够对准备参加数学建模竞赛的学弟学妹们提供一些帮助!

深入理解java虚拟机学习笔记 - java 虚拟机判断一个对象是否存活

java 虚拟机判断一个对象是否存活 判断一个对象是否存活依赖就是该对象是否被引用,下面主要介绍两种方法。 引用计数算法 给对象添加一个引用计数器,当对象被引用的时候计数器加1,当引用失效的时候计数器减1,当计数器为0的时候说明该对象没有被引用。 优点 实现起来比较简单 缺点 无法解决循环依赖的问题,A a = b; B b = a; 可达性分析算法 为了解决上述的遗留问题,即解...

微信公众号《后端学长》 231

STM32F407中文手册

STM32f407中文手册 本参考手册面向应用开发人员,提供有关使用 STM32F405xx/07xx、STM32F415xx/17xx、 STM32F42xxx 和 STM32F43xxx 微控制器存储器与外设的完整信息。STM32F405xx/07xx、STM32F415xx/17xx、STM32F42xxx 和 STM32F43xxx 构成一个微 控制器系列,各产品具有不同的存储器大小、封装和外设。有关订购信息以及器件的机械与电气特性,请参见数据手册。有关 ARM Cortex™-M4F 内核的信息,请参见《Cortex™-M4F 技术参考手册》。

判断Java对象是否存活的方法

0. 前言本文参考于《深入理解Java虚拟机:JVM高级特性与最佳实践》堆中几乎存放着Java世界中所有的对象实例,垃圾收集器在对堆回收之前,第一件事情就是要确定这些对象哪些还“存活”着,哪些对象已经“死去”(即不可能再被任何途径使用的对象),哪用什么办法去确认这些对象存活与否。在主流的商用程序语言中(Java和C#等),都是使用可达性分析算法(Reachability Analysis)来判断对象

腹黑大壁花 3477

JVM如何判断Java对象是否存活,是否要被GC回收?

GC在对堆内存进行垃圾清理之前,需要判断哪些Java对象不再被使用,需要被回收。通常有两种算法:引用计数算法、可达性分析算法。 引用计数算法(已被淘汰) 引用计数算法:在对象中添加一个引用计数器,每当有一个地方引用它时,计数器值就加一;当引用失效时,计数器值就减一;任何时刻计数器为零的对象就是不可能再被使用的。 存在的问题:主流的Java虚拟机里面都没有选用引用计数算法来管理内存,因为单纯的引用计...

西瓜游侠的博客 1505

如何判断对象是否存活

1.如何判断对象是否存活 1.1引用计数法 给对象中添加一个 引用计数器,每当有一个地方引用它时,计数器值+1,当引用失效时,计数器值-1。任何时刻计数器值为0的对象就是不可能再被使用的。但是这个方法有个问题不能解决:就是当两个对象相互引用时,他们的计数器值永远不会变成0,导致两个对象无法被回收。 1.2可达性分析算法 在主流的商用程序语言(Java、C#)的主流实现中,都是称通过可达性分析来判...

万事胜意 1186

如何判断一个对象是否存活?(或者GC对象的判定方法)?

这个问题,面试被问到的概率还是很大的。以下关于如何判断一个对象是否存活的回答,完全参照《深入理解Java虚拟机》一书,有需要的可以看书学习。以下是题目解析 判断对象是否存活的算法包括: 引用计数算法 可达性分析算法 问题的回答就是通过引用计数算法或者可达性分析算法去判断一个对象是否存活,下面开始具体描述这两种算法。 引用计数算法(Reference Countin...

知识分享 2688

深入理解Java虚拟机之判断对象是否存活算法

判断对象是否存活算法 引用计数法 给对象添加一个引用计数器,每当有一个地方引用它时,计数器就加1;当引用失效时,计数器就减1;任何时刻计数器为0的对象就是不可能再被使用的. 引用计数法的实现简单,判断效率很高,.**但主流的Java虚拟机并没有选用引用计数法来管理内存,主要原因是它很难解决对象之间相互循环引用的问题. public class Test{ private Object ...

可苯的博客 286

深入理解Java虚拟机——判断对象是否存活

目录一、判断对象是否存活的方式二、引用计数法2.1、引用计数法的概述2.2、引用计数法的缺点2.3、查看对象是否被回收掉三、可达性分析3.1、可达性分析的概述3.2、GC Roots的对象的概述 一、判断对象是否存活的方式 引用计数法 可达性分析 二、引用计数法 2.1、引用计数法的概述 给对象中添加一个引用计数器,每当有一个地方引用它时,计数器值就加1;当引用失效时,计数器值就减1; 任何时刻计数器为0的对象就是不可能再被使用的。 2.2、引用计数法的缺点 至少主流的java虚拟机里面没有选用引

小志的博客 794

深入理解Java虚拟机之判断对象是否存活

深入理解Java虚拟机之判断对象是否存活       我们知道Java虚拟机中对象的存储位置在堆上,所以GC回收主要也就是在堆上进行的,那么垃圾收集器在进行对象回收的时候肯定不能随便收集,必须要判断对象的状态是不是可以被收集,也就是说对象是不是已经“死亡”?那么垃圾收集器是如何判断对象是否已经死亡呢?        在Java虚拟机中判断对象是否死亡有两中算法,分别是引用计数算法和可达性分析算法。

国世的博客 1666

【跳槽面试】如何判断一个对象是否存活?(或者GC对象的判定方法)?

这个问题,面试被问到的概率还是很大的。以下关于如何判断一个对象是否存活的回答,完全参照《深入理解Java虚拟机》一书,有需要的可以看书学习。以下是题目解析判断对象是否存活的算法包括:引用计数算法可达性分析算法问题的回答就是通过引用计数算法或者可达性分析算法去判断一个对象是否存活,下面开始具体描述这两种算法。例如Object-C,Python语音使用引用计数算法进行内存管理。Java虚拟机没有选用引用计数器算法来管理内存,其中最主要的原因是它很难解决对象之间相互循环引用的问题。

技术分享 928

【26期】如何判断一个对象是否存活?(或者GC对象的判定方法)?

程序员的成长之路互联网/程序员/技术/资料共享关注阅读本文大概需要 3分钟。来自:www.jianshu.com/p/09a574dcd5df这个问题,面试被问到的概率还是很大的。以...

良月柒 703
上一篇: JimuReport积木报表—表达式介绍
下一篇: java中this关键字的使用
java111112313213
博客等级 码龄5年 15粉丝 73原创
评论
成就一亿技术人!
拼手气红包6.0元
还能输入1000个字符
 
 条评论被折叠 查看
添加红包

请填写红包祝福语或标题

个

红包个数最小为10个

元

红包金额最低5元

当前余额3.43元 前往充值 >
需支付:10.00元
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付元
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值