深入理解JVM学习笔记(十九、JVM 垃圾回收机制---如何判断对象是否为垃圾【引用计数法】)

一、引用计数法

        引用计数算法作为垃圾收集器最早的算法,有其优势,也有其劣势,虽然现在的JVM都不再采用引用计数算法进行垃圾回收【例如Sun的Java hotspot采用了火车算法进行垃圾回收】,但这种算法也并未被淘汰,在著名的单进程高并发缓存Redis中依然采用这种算法来进行内存回收。

        直白一点,引用计数算法就是对于创建的每一个对象都有一个与之关联的计数器,这个计数器记录着该对象被使用的次数,垃圾收集器在进行垃圾回收时,对扫描到的每一个对象判断一下计数器是否等于0,若等于0,就会释放该对象占用的内存空间,同时将该对象引用的其他对象的计数器进行减一操作。

        优势:简单易于垃圾回收器判定。

        劣势:采用引用计数器进行垃圾回收,最大的缺点就是不能解决循环引用的问题,例如一个父对象持有一个子对象的引用,子对象也持有父对象的引用,这种情况下,父子对象将一直存在于JVM的堆中,无法进行回收。

        接下来,我们写一个例子来佐证引用计数法的劣势,代码如下:

package com.zjt.test.jvm007;


public class Main {
	private Object instence;

	public Main() {
		//开辟一片20MB大小的内存,便于形象的看出释放效果
		byte [] b = new byte[20 * 1024 * 1024];
	}

	public static void main(String[] args) {
		//创建m1、m2.此时栈中有两个引用m1、m2分别指向堆中的两个Main中。
		Main m1 = new Main();
		Main m2 = new Main();
		
		//让堆中m1指向m2
		m1.instence = m2;
		//让堆中m2指向m1
		m2.instence = m1;
		
		//将栈队堆的引用断开
		m1 = null ;
		m2 = null ;
		
		//主动调用垃圾回收机制
		System.gc();
	}

}

运行后如下图所示:

        图中红框所示为回收前堆占用内存和回收后堆占用内存情况。 可以看出正好回收了40M,也就是两个Main的空间。因此可以得出结论:JDK8所采用的垃圾收集算法不是引用计数法

        可能你还有疑问,为什么你执行后没有打出这个日志呢,不要急,跟着我在eclipse上做以下简单配置在运行就可以了。

 

    运行即可。

 

 

 

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值