垃圾回收是发生在堆里,由垃圾回收器进行回收
堆是垃圾收集器管理的主要区域,由于现在收集器都采用分代收集算法,所以java堆还可以细分为新生代和老年代,再细一点有Eden空间 from survivor空间 to survivor空间等 从内存分配角度来看 线程共享的java堆中可能划分出多个线程私有的分配缓冲区
又可分为年轻代 老年代 永久代
年轻代:
所有新对象都是放在新生代,主要是尽可能快速收集生命周期短的对象 年轻代分为三个区,一个是Eden(伊甸区) 区 两个Survivor(幸存者)区
老年代:(生命周期长)
在年轻代经过了N次垃圾回收后仍然存活的对象,就会被放入老年代中
永久代
存放静态文件如java类 方法等
新创建的对象都放在伊甸区,当伊甸区满时,则进行垃圾回收扫描,把没用的对象回收,然后把存活的对象复制放入幸存者1区,然后清空伊甸区,然后又有创建新对象,把新对象放入伊甸区,当伊甸区满时,扫描,把存活对象复制放入幸存者2区,然后再扫描幸存者1区的对象是否存活,如果存活则一起复制到幸存者2区,否则清楚.幸存者1跟2必须有一个是空的,当幸存者区内存满时就把存活对象复制放入老年区
垃圾回收算法
引用计数器:就是在对象中放入一个计数器,当这个对象被引用时,计数器就+1,当没有引用时就-1.当计数器为0时,说明这个对象不可用了,就会被垃圾回收器回收。
优点:实用性 区域性
缺点:浪费cpu 无法解决循环问题
复制算法:将内存分为两部分,一部分使用,一部分预留,每次只使用其中的一部分 效率高 空间利用率低只有50%
标记清楚算法:(适用于老年代)根据GCroots作可达性分析,标记可达对象,然后反推,没有标记的就是垃圾,然后进行清楚,缺点:内存碎片化,经过垃圾回收后,垃圾对象被回收后,内存空间不会进行
标记压缩算法:
可达性分析算法: 通过一些被称为引用链(GC Roots)的对象作为起点,从这些节点开始向下搜索,搜索走过的路径被称为(Reference Chain),当一个对象到GC Roots没有任何引用链相连时(即从GC Roots节点到该节点不可达),则证明该对象是不可用的。
垃圾收集器
串行垃圾收集器
最基本历史最悠久的收集器
特点:针对新生代 使用复制算法,单线程收集 进行垃圾回收时 所有线程停止工作,直到完成
ParNew收集器
多线程
复制算法
CMS收集器
并发标记整理 针对老年代 基于标记清楚算法,不过不进行压缩操作,
G1收集器
特点:并行与并发 能充分利用cpu多核环境下的硬件优势,分代收集 收集范围包括新生代和老年代能独立管理gc堆不用跟其他收集器搭配,能够采用不同方式处理不同的对象
可作为GC Roots对象的包括如下几种:
虚拟机栈(栈桢中的本地变量表)中的引用的对象
方法区中的静态属性引用的对象
方法区中的常量引用对象
本地方法栈中的引用的对象



