面试题答案
一键面试1. 堆(Heap)
- 特点:
- 是Java虚拟机所管理的内存中最大的一块,被所有线程共享,用于存放对象实例以及数组。
- 大小可以通过参数 -Xms(初始堆大小)和 -Xmx(最大堆大小)进行调整。
- 对垃圾回收机制的影响:
- 回收策略:采用分代收集算法。将堆分为新生代和老年代。新生代又细分为Eden区和两个Survivor区(S0和S1)。
- 新生代:对象大多“朝生夕灭”,采用复制算法。当Eden区满时,触发Minor GC,将Eden区和其中一个Survivor区存活的对象复制到另一个Survivor区,清空Eden区和刚才使用的Survivor区。多次GC后仍存活的对象晋升到老年代。
- 老年代:对象存活时间较长,采用标记 - 清除算法或标记 - 整理算法。标记 - 清除算法先标记所有需要回收的对象,然后统一回收。标记 - 整理算法在标记后,将存活对象向一端移动,然后直接清理掉边界以外的内存。这是因为老年代对象存活率高,复制算法代价太大。
- 原因:分代收集算法基于对象的存活周期不同进行区分回收,提高回收效率。新生代对象更新频繁,复制算法简单高效,虽然会浪费一些空间但能快速回收;老年代对象移动代价大,标记 - 清除或标记 - 整理算法更适合。
- 回收策略:采用分代收集算法。将堆分为新生代和老年代。新生代又细分为Eden区和两个Survivor区(S0和S1)。
2. 栈(Stack)
- 特点:
- 每个线程都有自己的栈,线程私有。栈由栈帧组成,每个方法调用对应一个栈帧,包含局部变量表、操作数栈、动态链接、方法出口等信息。
- 栈的大小一般在几百KB到几MB之间,通过 -Xss参数设置。
- 对垃圾回收机制的影响:
- 回收策略:栈内存不需要垃圾回收,随着方法调用结束,栈帧自动弹出,栈空间被释放。
- 原因:栈内存的生命周期与线程相同,线程结束,栈内存自动释放,不需要复杂的垃圾回收机制。
3. 方法区(Method Area)
- 特点:
- 被所有线程共享,存储已被虚拟机加载的类信息、常量、静态变量、即时编译器编译后的代码等数据。
- 在JDK 1.8之前,习惯上称为永久代,1.8之后使用元空间(Metaspace)替代,元空间使用本地内存。
- 对垃圾回收机制的影响:
- 回收策略:方法区的垃圾回收主要回收两部分内容:废弃常量和无用的类。回收废弃常量与堆中对象回收类似。而判断一个类是否无用,需要满足以下条件:该类所有的实例都已经被回收,加载该类的ClassLoader已经被回收,该类对应的java.lang.Class对象没有在任何地方被引用,无法在任何地方通过反射访问该类的方法。由于满足这些条件的情况比较少,方法区的垃圾回收频率较低。
- 原因:方法区中数据的生命周期相对较长,常量和类信息等在程序运行期间可能一直被使用,所以垃圾回收频率低。而且判断类是否无用较为复杂,需要综合多方面因素判断。