jvm面试题(二)

参考《深入理解JVM》这本书,总结一下面试中常备问到的问题

5.如何判断对象可以被回收?

1.引用计数(有bug 不能解决循环引用的问题)

2.可达性分析:

  可选做GC Roots的对象包括以下几种:

  虚拟机栈(栈帧中局部变量表)中引用的数据

  方法区中静态属性引用的对象(static)

  方法区中常量引用的对象(final)

本地方法栈(native方法)中引用的对象

6.引用的分类

强引用:GC时不会被回收

软引用:描述有用但不是必须的对象,在发生内存溢出异常之前被回收

弱引用:描述有用但不是必须的对象,在下一次GC时被回收

虚引用(幽灵引用/幻影引用):无法通过虚引用获得对象,用PhantomReference实现虚引用,虚引用用来在GC时返回一个通知。

7.判断一个对象应该被回收

1.该对象没有与GC Roots相连

2.该对象没有重写finalize()方法或finalize()已经被执行过则直接回收(第一次标记)

、否则将对象加入到F-Queue队列中(优先级很低的队列)在这里finalize()方法被执行,之后进行第二次标记,如果对象仍然应该被GC则GC,否则移除队列。(在finalize方法中,对象很可能和其他 GC Roots中的某一个对象建立了关联,finalize方法只会被调用一次,且不推荐使用finalize方法)

8.回收方法区

方法区回收价值很低,主要回收废弃的常量和无用的类。

如何判断无用的类:

1.该类所有实例都被回收(java堆中没有该类的对象)

2.加载该类的ClassLoader已经被回收

3.该类对应的java.lang.Class对象没有在任何地方被引用,无法在任何地方利用反射访问该类


9.垃圾收集算法
1.标记-清除
先标记再清除、效率不高、产生碎片。
2.复制算法
内存划分为大小相等的两块,每次只使用一块,当这一块用完了就将对象中存活的对象复制到另一块上边。
效率较高、有内存被空闲不能完全利用。
商业虚拟机目前使用这种算法回收新生代。用8:1:1来分配eden:From Survivor: To Survivo,即可以使用90%的对象,survivor空间不够时需要老年代分配担保
3.标记-整理
标记之后将所有存活的对象向一端移动,不产生碎片

猜你喜欢

转载自blog.csdn.net/TRUE_LOVE1314/article/details/52262577