分代收集算法

现代商业虚拟机的垃圾回收机制都是采用分代收集算法(Generational Collection)算法,这种算法会根据对象存活周期的不同将内存划分为几块,这样就可以根据各个区域的特点采用最适当的收集算法。
对内存可分为新生区、养老区永久存储区三个区域。
新生区,每次垃圾收集都有大批对象死去,只有少了存活,所以可以用复制算法。
养老区,因为对象存活率高、没有额外空间对它进行担保,必须使用标记-清除或标记-整理算法进行回收。

  1. ![](https://cdn.nlark.com/yuque/0/2021/png/2955945/1618190402448-aef78ca7-1d73-4520-933c-0d2544289685.png#align=left&display=inline&height=429&margin=%5Bobject%20Object%5D&originHeight=429&originWidth=619&size=0&status=done&style=none&width=619)

1 新生区(Young Generation Space)

新生区是类的诞生、成长、消亡的区域。
新生区有分为伊甸区、幸存者区两部分。

  1. - **伊甸区(Eden Space)**

大多数情况下,对象都是在伊甸区中分配的,当伊甸区没有足够的空间进行分配时,虚拟机将发起一次Minor GC。Minor GC 是指发生在新生区的垃圾回收动作,Minor GC 非常繁忙,回收速度也比较快。
当伊甸区的空间用完时,GC 会对伊甸区进行垃圾回收,并把伊甸区剩下的对象移到幸存0区。

  1. - **幸存0区(Survivor 0 Space)**

如果幸存0区满了,GC 会对该区域进行垃圾回收,然后把该 区域剩下的对象移动到幸存1区。

  1. - **幸存1区(Survivor 1 Space)**

如果幸存1区满了,GC 会对该区域进行垃圾回收,然后把幸存1区中的对象移动到养老区。

2 养老区(Tenure Generation Space)

养老区用于保存从新生区筛选出来的 Java 对象。
当幸存1区尝试移动对象到养老区,但是发现空间不足时,虚拟机会发起一次 Major GC。Major GC 的速度一般比 Minor GC 慢 10 倍以上。
大对象直接进入养老区,比如很大的数字和很长的字符串。

3 永久存储区(Permanent Space)

永久存储区是一个常驻内存区域,用于存放 JDK 自身携带的 Class Interface 元数据。
永久存储区存储的是运行环境必需的类信息,被装载进该区域的数据是不会被垃圾回收器回收掉的,只有 JVM 关闭时才会释放此区域的内存。