什么是Java的垃圾回收?
自动管理内存的机制,负责自动释放不再被程序引用的对象所占用的内存。
怎么触发垃圾回收?
- 内存不足时:JVM检测到堆内存不足时,无法为新的对象分配内存时,会自动触发垃圾回收。
- 手动请求: 调用System.gc()或者Runtime.getRuntime().gc(),JVM会尝试进行垃圾回收(不能保证执行)。
怎么判断对象是否为垃圾,是否要被回收?
- 引用计数法: 为每个对象分配一个引用计数器,每当有一个地方引用它时,计数器加1,引用失效时,计数器减1。为0时表示可以被回收。缺点是不能解决循环引用的问题。
- 可达性分析: 从Gc Roots出发,向下追溯它们引用的对象,以及这些对象引用的其他对象。如果一个对象到Gc Roots没有任何引用链相连,说明该对象不可达,可以被回收。
GC Roots对象包括:虚拟机栈中引用的对象,本地方法栈中引用的对象,静态属性引用的对象,方法区常量引用的对象。
垃圾回收算法有哪些?
- 标记清除:通过可达性分析,先标记出所有需要回收的对象,然后再统一回收所有被标记的对象。缺点是效率不高,还会造成大量的碎片空间。
- 复制:将内存分为两块,分配内存时只使用一块,内存不够时将存活的对象复制到另一块上去,然后将这一块清空。
- 标记整理:先标记,再将所有存活对象移到到内存的一端。
- 分代回收:将内存划分为新生代和老年代。新生代经历一次GC后将存活的对象年龄加1,年龄超过一定值就放到老年代去。
垃圾回收器有哪些?
(这里就写几个,多了记不住)
- Serial收集器(复制算法):串行回收,作用于新生代。单线程,效率高。
- CMS(Concurrent Mark Sweep)收集器(标记清除):并发回收,作用于老年代。高并发,低停顿。
- G1收集器(标记整理):并行并发收集器,作用于整个堆,包括新生代和老年代。
CMS和G1的区别
- 作用范围不一样:CMS作用于老年代,G1作用于新生代和老年代。
- STW的时间:CMS以最小的停顿时间为目标,G1可预测停顿时间。
- 算法不一样:CMS是标记清除,G1是标记整理。
- 垃圾碎片:CMS使用垃圾清除,容易产生内存碎片。G1使用标记整理,没有内存碎片。
什么场景触发Full GC?
Full GC: 对整个堆内存进行回收
触发条件:
- 直接调用System.gc()或者Runtime.getRuntime().gc(),不能保证立即执行,但会尝试。
- 新生代垃圾回收时,如果存活的对象无法全部放入老年代,或者老年代空间不足了,就会触发Full GC。
- 元空间空间不足。
minorGC、majorGC
- minorGC:只针对新生代进行回收。Eden空间不足,就会触发minorGc。发生得很频繁,因为新生代中对象生命周期较短,回收效率高。
- majorGC:主要针对老年代进行回收,但不一定只回收老年代。老年代空间不足就会触发majorGC。