JVM是Java的运行基础,面试的时候一定会问到,而这一部分平常在做项目的时候很少了解到。所以这块知识点偏理论知识,需要了解的东西也有很多。
到了大三的学期的暑假,即将面临找工作的考验。希望这份面试资料能够帮住大家学到自己的知识盲区。加油,我命由我不由天!!!
垃圾回收不会发生在永久代,如果永久代满了或者超过了临界值,会触发完全垃圾回收(Full GC)。如果仔细查看垃圾收集器的输出信息,就会发现永久代也是被回收的。这就是为什么正确的永久代大小对避免Full GC是非常重要的原因。
GC最基础的算法有三种:标记-清除算法、复制算法、标记压缩算法,我们常用的垃圾回收器一般采用分代收集算法。
1、标记-清除算法,如它名字一般,算法分为”标记“和”清除“俩个阶段;首先标记出所有需要回收的对象,在标记完成后统一回收掉所有被标记的对象。
2、复制算法,它将可用的内存按容量划分为大小相等的俩块,每次只使其中的一块,当这一块内存用完,就将还存活的对象复制到另一块上面,然后再把已使用的内存空间一次清理掉。
3、标记压缩算法,标记过程仍然与”标记“,”清除“算法一样,但后续步骤不是直接对可回收对象进行清理,而是让所有存活的对象都向一段移动,然后直接清理掉端边界以外的内存。
4、分代收集算法,“分代收集法“把java堆分为新生代和老年代,这样就可以根据各个年代的特点采用最适当的收集算法。
新生代内存不够用时发生MGC也叫YGC,JVM内存不够的时候发生FGC
1、设定堆内存大小
Xmx:堆内存最大限制。
2、设定新生代大小。新生代不宜太小,否则会有大量对象涌入老年代
XX:NewSize:新生代大小
XX:NewRatio:新生代和老年代对比
XX:SurvivorRatio:伊甸园空间和幸存者空间的占比
如果在HotSpot虚拟机上开发、部署,很多程序员都把方法去称作永久代哦,可以说方法区是规范,永久代是HotSpot针对该规范进行的实现。在java7版本之前,方法区都是永久代实现的。
对于java8,HotSpots取代了永久代,取而代之的是元空间。换句话说,就是方法区还在,只是实现变了,从永久代变成了元空间。
JVM包含俩个子系统和俩个组件,分别为:
**1、Class loader(类装载子系统):**根据给定的全限名定类名(如:java:lang.Object)来装载class文件到运行时数据区的方法中。
**2、Execution engine(执行引擎子系统):**执行class指令
**3、Runtime data area(运行时数据区组件):**与native lib交互,是其它编程语言交互的接口
4、Native interface(本地接口组件): JVM内存
一般情况下,JVM的对象都堆放在堆内存中。当类加载检查通过后,java虚拟机开始为新生代分配内存。如果java堆中内存是绝对规整的,所有被使用过的内存都放到一边,空闲的内存放到另一边,中间放着一个指针作为分界点的指示器,所分配内存仅仅是把那个指针向空闲空间方向挪动一段与对象大小相等的实例,这种分配方式就是指针碰撞。

如果Java堆内存中的内存并不是规整的,已被使用的内存和空闲的内存相互交错在一起,不可以进行指针碰撞啦,虚拟机必须维护一个列表,记录哪些内存是可用的,在分配的时候从列表找到一块大的空间分配给对象实例,并更新列表上的记录,这种分配方式就是空闲列表。
可以把内存分配的动作按照线程划分在不同的空间之中进行,每个线程在Java堆中预先分配一小块内存,这就是TLAB(Thread Local Allocation Buffer,本地线程分配缓存) 。虚拟机通过 -XX:UseTLAB 设定它的。
JVM虚拟机这一块知识点,不仅在学校课中很少认真学习过,而且私下没有认真去了解。对知识点非常的生疏。很多的名词和专业术语都很陌生,学起来有点吃力,这仅是我个人的问题。希望能够坚持下去。