【JVM】JVM执行引擎

来源:互联网 发布:软件著作权申请加急 编辑:程序博客网 时间:2024/06/05 01:17

【JVM】JVM执行引擎

作用: 执行字节码,或者执行本地方法

Java虚拟机的主要任务是装在class文件并且执行其中的字节码。Java虚拟机包含一个类装载器,它可以从程序和API中装载class文件。Java API中只有程序执行时需要的那些类才会被装载。字节码由执行引擎来执行。不同的Java虚拟机中,执行引擎可能实现得非常不同。在由软件实现的虚拟机中,最简单的执行引擎就是一次性解释字节码。

另一种执行引擎更快,但是也更消耗内存,叫做”即时编译器(just-in-time compiler)”。在这种情况下,第一次被执行的字节码会被编译成本地机器代码。编译出的本地机器代码会被缓存,当方法以后被调用的时候可以重用。

第三种执行引擎是自适应优化器。在这种方法里,虚拟机开始的时候解释字节码,但是会监视运行中程序的活动,并且记录下使用最频繁的代码段。程序运行的时候,虚拟机只把那些活动最频繁的代码编译成本地代码,其他的代码由于使用得不是很频繁,继续保留为字节码,由虚拟机继续解释它们。
一个自适应的优化器可以使得Java虚拟机在80%~90%的时间里执行被优化过的本地代码,而只需要编译10%~20%的对性能有影响的代码。

JVM之字节码执行引擎
执行引擎在执行Java代码时候可能会有解释执行和编译执行两种选择,也可能两者兼备,甚至还可能会包含几个不同级别的编译器执行引擎。

栈帧

局部变量表
操作数
动态连接
方法返回地址
附加信息

方法调用
解析
方法在程序真正运行之前就有一个可确定的调用版本,并且这个方法的调用版本在运行期是不可变的。

invokestatic
invokespecial
invlkevirtual
invokeinterface
invokedynamic

分派
1.静态分派

静态类型(Static Type)
实际类型(Actual Type)
静态类型在编译期就可知,实际类型只有在运行期才能确定。
所有依赖静态类型来定位方法执行版本的分派动作称为静态分派,典型应用时方法重载。

2.动态分派

重写(Override)
运行期根据实际类型确定方法执行版本的分派过程称为动态分派

3.单分派与多分派

方法的接收者与方法的参数统称为方法的宗量。根据分派基于多少种宗量,可以将分派划分为单分派和多分派两种。单分派是根据一个宗量对目标方法进行选择,多分派则是根据多于一个宗量对目标方法进行选择。

虚拟机动态分派的实现

虚方法表
接口方法表

动态类型语言支持

  1. 动态类型语言
    什么是动态类型语言?动态类型语言的关键特征是它的类型检查的主体过程是在运行期而不是在编译期。如JavaScript,Lua,静态类型语言如C++、Java
  2. JDK1.7与动态类型
  3. java.lang.invoke包

MethodHandle与反射的区别

1) 从本质上讲,Reflection和MethodHandle机制都是在模仿方法的调用,但Reflection是在模拟Java代码层次的方法调用,而MethodHandle是在模拟字节码层次的方法调用。

2) Reflection中的java.lang.reflect.Method对象远比MethodHandle机制中的java.lang.invoke.MethodHandle对象所包含的信息多。前者是方法在Java一端的全面映像,包含了方法的签名、描述符以及方法属性表中各个属性的Java端表示方式,还包含执行权限等运行期信息。而后者仅仅包含于执行该方法相关的信息。用通俗的话来将,Reflection是重量级的,而MethodHandle是轻量级。

3)由于MethodHandle是对字节码的方法指令调用模拟,所以理论上虚拟机在这方面做的各种优化,在MethodHandle上也应当可以采用类似思路去支持。而通过反射去调用方法则不行。

4.invokedynamic指令

5.掌控方法分派规则

参考:
《深入理解Java虚拟机:JVM高级特性与最佳实践》及其他文档


声明:图片来自源于网络。这是之前整理的word笔记,没有注明图片具体来源,抱歉。在此向贡献图片的人表示感谢。