内存分配和回收策略

  对象的内存分配,大方向上来说就是在堆上分配(但也可能经过JIT编译后被拆散为标量类型并间接地栈上分配),主要对象分配在新生代的Eden区,如果启动了本地分配缓冲,将按照线程优先在TLAB(Thread Local Allocation Buffer)上分配。少数情况下也可能直接分配到老年代中,这些规则取决于采用的垃收集集器组合,还有虚拟机中与内存相关参数的设置。

1.对象优先在Eden分配

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

  注:新生代GC(Minor GC):指发生在新生代的垃圾收集动作,因为大多Java对象寿命短暂,所以Minor GC非常频繁,回收速度快。

    老年代GC(Major GC/Full GC):指发生在老年代的GC,出现了Major GC,经常伴随着至少一次的Minor GC(但并非绝对的,在   Parallel Scavenge收集器的收集策略里就有直接进行Major GC的策略选择过程),Major GC的速度一般会比Minor GC慢10倍以上。

2.大对象直接进入老年代

    大对象是指:需要大量连续内存空间的Java对象,最典型的大对象就是那种很长的字符串以及数组。虚拟机提供了一个

  -XX: PretenureSizeThreshold参数,令大于这个设置值的对象直接进入老年代,这样避免了大对象在Eden区以及两个Survivor之间发  生大量的内存复制(复习:新生代采用复制算法收集内存)。

  注:PretenureSizeThreshold参数只对Serial和PreNew两款收集器有效,Parallel Scavenge收集器不认识这个参数,

  Parallel Scavenge收集器一般不需要设置,如果用到必须要使用此参数的场合,可以考虑ParNew+CMS收集器组合。

3.长期存活的对象进入老年代

    虚拟机给每个对象定义了一个对象年龄(Age)计数器,如果对象在Eden出生并经过第一次Minor GC后仍然存活,并且能被Survivor  容纳的话,将被移动到Survivor空间中,并且年龄设为1.对象在Survivor中每熬过一次Minor GC,年龄就增加一岁,当年龄增加到一定程  度(默认15岁),将会被晋升到老年代。年龄阈值可以通过参数-XX:MaxTenuringThreshold设置。

4.动态对象年龄判定

    虚拟机并不是永远地要求对象的年龄必须达到了MaxTenuringThreshold才能晋升老年代,如果在Survivor空间中相同年龄所有对象大  小总和大于Survivor空间的一半,年龄大于或等于该年龄的对象就可以直接进入老年代,无需等到MaxTenuringThreshold中要求的年龄。

5.空间分配担保

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

时间: 2024-10-07 05:55:30

内存分配和回收策略的相关文章

垃圾收集器与内存分配策略(六)之内存分配与回收策略

垃圾收集器与内存分配策略(六)--内存分配与回收策略 对象的内存分配,一般来说就是在堆上的分配(但也可能经过JIT编译后被拆散为标量类型并间接地栈上分配),对象分配的细节取决于当前使用的是哪一种垃圾收集器组合,还有虚拟机中与内存相关的参数设置. 区分Minor GC与 Full GC: 新生代GC(Minor GC):指发生在新生代的的垃圾收集动作,因为Java对象大多具有朝生夕灭的特性,所以Minor GC非常频繁,一般回收速度也比较快. 老年代GC(Full GC / Major GC):老

二 内存分配与回收策略

内存分配与回收策略 对象的内存分配,往大方向讲,就是在堆上分配(但也可能经过JIT编译后被拆散为标量类型并间接在栈上分配),对象主要分配在新生代的Eden区上,如果启动了本地线程分配缓冲,将线程优先在TLAB上分配,少数情况下也可能直接分配在老年代中. 对象优先在Eden分配  大多数情况下,对象在新生代Eden区中分配.当Eden区没有足够空间进行分配时,虚拟机讲发起一次MinorGC. 大对象直接进入老年代 所谓的大对象是指,需要大量连续内存空间的Java对象,最典型的大对象就是那种很长的字

java虚拟机(3)--内存分配与回收策略

三.内存分配与回收策略 1.1 Minor GC 和 Full GC Minor GC:发生在新生代上,因为新生代对象存活时间很短,因此 Minor GC 会频繁执行,执行的速度一般也会比较快. Full GC:发生在老年代上,老年代对象其存活时间长,因此 Full GC 很少执行,执行速度会比 Minor GC 慢很多. 1.2 内存分配策略 1.2.1            对象优先在 Eden 分配 大多数情况下,对象在新生代 Eden 区分配,当 Eden 区空间不够时,发起 Minor

【深入理解JVM】:内存分配与回收策略

Java技术体系中所提倡的自动内存管理最终可以归结为自动化地解决了两个问题:给对象分配内存以及回收分配给对象的内存. 对象的内存分配,往大方向讲,就是在堆上分配,对象主要分配在新生代的Eden区上,如果启动了本地线程分配缓冲,将按线程优先在TLAB上分配.少数情况下也可能会直接分配在老年代中,分配的规则并不是百分之百固定的,其细节取决于当前使用的是哪一种垃圾收集器组合,还有虚拟机中与内存相关的参数的设置. 本文中的内存分配策略指的是Serial / Serial Old收集器下(ParNew /

JVM之内存分配与回收策略

前言 对象的内存分配,往大的方向上讲,就是在堆上分配,少数情况下也可能会直接分配在老年代中,分配的规则并不是百分之百固定的,其细节决定于当前使用的是哪种垃圾收集器组合,当然还有虚拟机中与内存相关的参数.垃圾收集器组合一般就是Serial+Serial Old和Parallel+Serial Old,前者是Client模式下的默认垃圾收集器组合,后者是Server模式下的默认垃圾收集器组合,文章使用对比学习法对比Client模式下和Server模式下同一条对象分配原则有什么区别. TLAB 首先讲

内存分配与回收策略

前言:垃圾回收 和内存分配是jvm中重要的两个部分,这个笔记,记载的是JVM的内存分配策略.   1.对象优先在新生代的Edon区分配.   2.大对象直接进入老年代.   3.长期存活的对象进入老年代.

浅谈java内存分配和回收策略

一.导论 java技术体系中所提到的内存自动化管理归根结底就是内存的分配与回收两个问题,之前已经和大家谈过java回收的相关知识,今天来和大家聊聊java对象的在内存中的分配.通俗的讲,对象的内存分配就是在堆上的分配,对象主要分配在新生代的Eden上(关于对象在内存上的分代在垃圾回收中会补上,想了解的也可以参考<深入理解java虚拟机>),如果启动了本地线程分配缓冲,讲按线程优先在TLAB上分配.少数情况下也是直接在老年代中分配. 二.经典的分配策略 1.对象优先在Eden上分配 一般情况下对

《深入理解Java虚拟机》笔记 第三章 内存分配与回收策略

几条主要的最普遍的内存分配规则: ? ? 1.对象优先在Eden分配 ? 大多数情况下,对象在新生代的Eden区中分配. ? ? 当Eden区没有足够的空间进行分配时,虚拟将发起一次Minor GC,如果GC后新生代中存活的对象无法全部放入Survivor空间,则需要通过分配担保机制提前进入到老年代中,前提是老年代中不能容纳所有存活对象,即只能容纳部分. ? ? 则未能进入到老年代的存活对象将继续分配在Eden区中 ? ? 如果Eden区也还未能容纳剩余的存活对象虚拟机抛出OutOfMemory

深入理解Java虚拟机笔记---内存分配与回收策略

Java技术体系中的自动内存管理最终可以归结为自动化地解决了两个问题:给对象分配内存以及回收分配给对象的内存.对象的内存分配往大的方向上讲,就是在堆上分配,对象主要分配在新生代的Eden区上,如果启动了本地线程分配缓冲(-XX:+UseTLAB,默认已开启),将按线程优先在TLAB上分配.少数情况下也可能会直接分配在老年代中,分配的规则并不是百分之百固定的,其细节取决于当前使用的是哪一种垃圾收集器组合,还有虚拟机中与内存相关的参数设置. 下面是几条主要的最普遍的内存分配规则: 1.对象优先在Ed