"GC简要介绍,涵盖了垃圾收集算法、垃圾搜索算法以及可能遇到的问题和收集器的相关知识。"
在Java编程语言中,垃圾收集(Garbage Collection,简称GC)是一项自动内存管理机制,用于回收不再使用的对象所占用的内存空间,以防止内存泄漏。GC的主要目标是确保程序的稳定运行并优化内存利用率。
### GC搜索算法
1. **引用计数法**:每个对象都有一个引用计数,当对象被引用时计数加1,引用失效时减1。但这种方法无法处理循环引用的情况,即两个对象相互引用,而其他对象不再引用它们时,这两个对象都无法被正确地回收。
2. **根搜索算法**:这是Java采用的主要方式,从一组称为“GC Roots”的对象开始,如虚拟机栈中的引用对象、方法区中的类静态属性引用、常量引用和本地方法栈中的JNI引用,沿着引用链向下搜索,可达的对象被认为是存活的,不可达的对象则被视为垃圾。
### GC收集算法
1. **标记-清楚算法**:首先标记所有存活的对象,然后清除未被标记的对象。这种算法会产生大量的空间碎片,影响内存的连续分配。
2. **复制算法**:将内存分为两等份,每次只使用一半,垃圾收集时将存活对象复制到另一半,然后清空使用过的区域。优点是避免了碎片,但缺点是浪费了一半的内存。
3. **标记-整理算法**:标记存活对象后,将它们移动到内存的一端,然后清理边界外的对象。解决了碎片问题,但移动对象可能会影响性能。
4. **分代收集算法**:根据对象的生命周期将内存分为新生代(Young Generation)和老年代(Old Generation),不同代使用不同的收集策略。新生代对象生存时间短,适合复制算法;老年代对象生存时间长,适合标记-整理或标记-清楚。
### 引用类型
1. **强引用**:最常见的引用,只要强引用存在,对象就不会被GC回收。
2. **软引用**:在系统即将发生内存溢出之前,会回收软引用对象。
3. **弱引用**:在下一次GC时,无论内存是否充足,都会回收弱引用对象。
4. **虚引用**:不直接控制对象的生命周期,主要用于获取对象被GC回收的通知。
### 方法区的废弃常量与对象收集
废弃常量的回收相对简单,而废弃对象的回收需满足三个条件:所有实例已被回收,加载类的ClassLoader被回收,且类本身没有被引用。
### 垃圾收集器
- **分代收集器**:根据对象生命周期特点,对不同代使用不同收集器。
- **年轻代(Young Generation)**:
- **Serial收集器**:单线程,简单高效,但在垃圾收集时暂停所有线程。
- **ParNew收集器**:Serial的多线程版本,常与CMS配合。
- **ParallelScavenge收集器**:关注吞吐量,可调整参数以优化性能。
垃圾收集器的选择和配置对应用性能有很大影响,需要根据应用场景和需求进行调整。理解这些基本概念和原理对于优化Java应用的内存管理至关重要。