JAVA 垃圾回收 --《JAVA编程思想》15

JAVA 提供垃圾回收器释放内存,防止内存泄露,无需程序员手动释放内存,减轻了编码的负担。那么它究竟是如何工作呢,今天就和大家一探究竟。

我们先来看看 C++ 是如何释放内存的,C++ 里每个对象都负责管理自己的内存,通过析构函数释放内存,倘若程序员未执行析构函数,则内存在程序终止之前,永远不会得到释放,易造成内存泄露。

在 JAVA 中有一个特殊的函数 finalize() ,在对象被垃圾回收器清理之前,会被调用。但需特别注意的是,调用 finalize() 不一定立马会被垃圾回收器清理,只有当程序无法获得足够的内存时,才会被清理。通常可以使用 finalize() 来进行对象终结条件的验证,例如:一个对象打开了一个文件,在对象被清理时,验证文件是否被关闭。

接下来,来实际看看垃圾回收器是如何工作的。JAVA 对象存放于中,通过“堆指针”来为对象分配内存空间,每分配一个新对象,指针就往前移动一格,分配的速度非常快,但内存资源是有限的,当内存资源即将耗尽时,垃圾回收器便会介入。

垃圾回收器一边回收空间,一边将堆中的对象紧凑排列,实现了一种高速、有无限空间可供分配的堆模型。

JAVA 的垃圾回收器是如何辨别需要回收的对象呢?

当一个对象不再被其他对象引用的时候,就会被列入垃圾回收的名单。

不同的 JAVA 虚拟机拥有不同的垃圾回收模式:

1.停止–复制模式(stop-and-copy)
先暂停程序的运行(不能在后台进行回收),将所有存活的对象从当前堆复制到另一个堆中,未被复制的对象,会被当做垃圾进行回收,复制到新堆的对象会被紧凑排列。

这种模式效率较低,至少得保持两个堆进行复制,还得多维护一倍的内存空间。此机制无法在前台运行,程序在此期间会被暂停运行。

2.标记–清扫模式(mark-and-sweep)
每找到一个活的对象,就会给对象一个标记,此时不会清理任何对象。当全部标记工作完成时,清理动作才会开始执行,没有标记的对象会被释放,不会发生任何复制动作,但剩下的堆空间不连续,此模式也无法在后台运行,程序会被暂停运行。

3.自适应模式
内存分配以“”为单位,对象较大则占用单独的,对象较小则共用一个块,每个块上都拥有相应的代数来记录对象是否存活。如果“块”新增一个引用,则“块”上的“代数”就加一;减少一个引用,“块”上的“代数”减一。对大对象的块使用“标记–清扫模式”(减轻维护堆空间的压力),对小对象共用的块使用“停止–复制模式”(对处理临时短命对象大有提升),倘若垃圾回收器的效率降低,则仅仅会使用“标记–清扫模式”。

本次分享至此结束,希望本文对你有所帮助,若能点亮下方的点赞按钮,在下感激不尽,谢谢您的【精神支持】。

若有任何疑问,也欢迎与我交流,若存在不足之处,也欢迎各位指正!

评论 1
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

BaymaxCS

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值