jvm讲解

一、程序源代码

jvm讲解_第1张图片

二、程序在jvm中的执行过程。

jvm讲解_第2张图片

三、jvm指令码

jvm讲解_第3张图片

三、栈

每个线程都会从占内存中获取一块内存空间,例如:线程main就是从栈内存中获取的一小块内存空间。
栈是由一块一块的栈帧组成,里面的栈帧有“最先进,最后出”的规则,就像枪的子弹夹一样。

1、栈帧

每个线程中可能涉及打不同方法的相互调用,每个方法都会分配一块内存区域就是栈帧,栈(也就是一个线程)是由一块块栈帧组成。
栈帧内部最核心的是由四块组成:局部变量表、操作数栈、动态链接、方法出口。
(1)操作数栈:临时的一块内存区域,用来程序运行中临时存放操作数。
例、当代码执行 int a = 1 时,jvm指令 iconst_1 将int类型常量1压入操作数栈

(2)局部变量表:如果放的是对象类型,放的是堆内存里面的对象的引用地址。
jvm指令istore_1会在局部变量表中给局部变量a分配一块内存区域,然后把常量1放到局部变量a中。

(3)方法出口
记录当本方法执行完之后,回到主方法时改从哪一行执行。

例:当执行compute方法时,此时已经将调用此方法的位置记录到方法出口里面了,当compute方法执行完毕,继续从主函数的这一行开始执行。

四、程序计数器

每个线程会有一个独有的程序计数器,记录线程运行到哪一行的代码的位置,程序计数器值的改变是由字节码执行引擎去改变的。

**作用:**当cpu的执行权由其他线程抢去,当前线程要挂起,恢复当前线程的时候要知道从哪一行开始执行,程序计数器的作用就是知道要从哪一行开始恢复执行。

jvm讲解_第4张图片

五、方法区

放置常量、静态变量、类信息(math.class)

六、本地方法栈

本地方法(native修饰的方法)在运行过程中需要的一块区域。

七、堆内存详解

jvm讲解_第5张图片
新new出来的对象先放在Eden区,当Eden区放满,jvm会进行minor GC(垃圾收集)操作。
jvm讲解_第6张图片
凡是在链条上找到的对象,都认为不是垃圾对象,会执行一个复制算法,将这些对象复制到From区,此时当前这些对象的分代年龄会加一;当Eden区又放满对象,会再次进行minor GC(垃圾收集)操作,此时“Eden区”和“From区”未被回收的对象会移到“To”区,此时这些对象的分代年龄会再次加一;当Eden区又放满对象,会再次进行minor GC(垃圾收集)操作,此时“Eden区”和“To区”未被回收的对象会移到“From”区,此时这些对象的分代年龄会再次加一。
当对象的分代年龄增长到15,会将这样的对象放到“老年代”,例如(对象类型的静态变量、缓存、线程池中的对象、spring bean容器中的对象),当老年代放满对象的时候,会出现full gc,此时会进行STW(stop the world),将我们用户的应用线程停掉,此时的用户体验非常不好,我们做jvm的调优,目的就是减少STW的出现。

八、jvm调优方案

知识点:当一批对象被移到Survior区,会将移进来的对象与Survior区大小进行一个比对,当超过Survior区大小的50%以上了,动态年龄判断机制会将这一批对象直接放进老年代,此时老年代很容易就放满,老年代就会触发full gc。

场景:双十一促销,刚过12点,抢购下单的时候。
方案:调小老年代大小,调大年轻代大小。

你可能感兴趣的:(jvm,jvm,栈,堆栈)