200字范文,内容丰富有趣,生活中的好帮手!
200字范文 > 深入理解java虚拟机-读书笔记2-垃圾收集器和内存分配策略

深入理解java虚拟机-读书笔记2-垃圾收集器和内存分配策略

时间:2024-06-17 19:41:24

相关推荐

深入理解java虚拟机-读书笔记2-垃圾收集器和内存分配策略

垃圾回收重点区域:堆和方法区部分区域。

引用计数算法:

1,引用计数算法:

给对象中添加一个引用计数器,每当有一个地方引用它时,计数器值就加1;当引用失效时,计数器值就减1;任何时刻计数器都为0的对象就是不再被使用的,垃圾收集器将回收该对象使用的内存。

实现简单,判定效率很高。但是很难解决对象之间循环引用的问题。

2,可达性分析算法:

java所使用的垃圾回收算法。

基本思想:通过一系列的名为“GC Root”的对象作为起点,从这些节点向下搜索,搜索所走过的路径称为引用链(Reference Chain),当一个对象到GC Root没有任何引用链相连时,则该对象不可达,该对象是不可使用的,垃圾收集器将回收其所占的内存。

在java中,可作为GC Roots的对象包括下面几种:

a,虚拟机栈(栈帧中的本地变量表)中引用的对象

b,方法区中类静态属性引用的对象

c,方法区中常量引用的对象

d,本地方法栈中JNI(即Native方法)引用的对象

垃圾收集算法:

- 标记-清除算法

缺点:首先,效率问题,标记和清除效率都不高。其次,标记清除之后会产生大量的不连续的内存碎片,空间碎片太多会导致当程序需要为较大对象分配内存时无法找到足够的连续内存而不得不提前触发另一次垃圾收集动作。

- 复制算法

每次都是对其中一块内存进行回收,内存分配时不用考虑内存碎片等复杂情况,只需要移动堆顶指针,按顺序分配内存即可,实现简单,运行高效。

复制算法的缺点显而易见,可使用的内存降为原来一半。

- 标记-整理算法

标记-整理算法在标记-清除算法基础上做了改进,标记阶段是相同的标记出所有需要回收的对象,在标记完成之后不是直接对可回收对象进行清理,而是让所有存活的对象都向一端移动,在移动过程中清理掉可回收的对象,这个过程叫做整理。

标记-整理算法相比标记-清除算法的优点是内存被整理以后不会产生大量不连续内存碎片问题。

复制算法在对象存活率高的情况下就要执行较多的复制操作,效率将会变低,而在对象存活率高的情况下使用标记-整理算法效率会大大提高。

- 分代收集算法

根据对象存活周期不同将内存划分为几块,一般是将堆分为新生代和老年代:

1,新生代,采用复制算法,只需要付出少量存活对象的复制成本

2,老年代,采用标记-清除或者标记-整理。

**

垃圾收集器:

内存分配与回收策略:

- 对象优先在eden分配

大多数情况对象在新生代Eden区分配,当Eden区没有足够空间进行分配时,虚拟机将发起一次Minor GC

- 大对象直接进入老年代

所谓大对象就是指需要大量连续内存空间的Java对象,最典型的大对象就是那种很长的字符串以及数组。这样做的目的是避免Eden区及两个Servivor之间发生大量的内存复制

- 长期存活的对象将进入老年代

如果对象在Eden区出生并且经历过一次Minor GC后仍然存活,并且能够被Servivor容纳,将被移动到Servivor空间中,并且把对象年龄设置成为1.对象在Servivor区中每熬过一次Minor GC,年龄就增加1岁,当它的年龄增加到一定程度(默认15岁),就将会被晋级到老年代中

- 动态对象年龄判定

为了更好地适应不同程序的内存状况,虚拟机并不是永远地要求对象的年龄必须达到了MaxTenuringThreshold才能晋级到老年代,如果在Servivor空间中相同年龄所有对象的大小总和大于Survivor空间的一半,年龄大于或等于该年龄的对象就可以直接进入到老年代,无须等到MaxTenuringThreshold中要求的年龄

- 空间分配担保

在发生Minor GC 之前,虚拟机会检查老年代最大可 用的连续空间是否大于新生代所有对象总空间,如果这个条件成立,那么Minor DC可以确保是安全的。如果不成立,则虚拟机会查看HandlePromotionFailure设置值是否允许担保失败。如果允许那么会继续检查老年代最大可用的连续空间是否大于晋级到老年代对象的平均大小,如果大于,将尝试进行一次Minor GC,尽管这次MinorGC 是有风险的:如果小于,或者HandlePromotionFailure设置不允许冒险,那这时也要改为进行一次Full GC

本内容不代表本网观点和政治立场,如有侵犯你的权益请联系我们处理。
网友评论
网友评论仅供其表达个人看法,并不表明网站立场。