java虚拟机类加载以及class中字节码的执行

版权声明:本文为博主原创文章,未经博主允许不得转载。 https://blog.csdn.net/l450741881/article/details/88131774

一.jvm类加载

java类在遇到1.类似new指令;2.反射调用;3.子类加载;4包含main函数;的时候会在虚拟机中加载该类,加载的大体步骤为:

加载->验证->准备->解析->初始化

1.加载

加载类主要完成的工作为:1.找到该类并获取class中的二进制字节流;2.将二进制字节流转化成可以运行的运行时数据;3.方法区中生成访问该对象的入口,堆内存中生成改类对象

类的加载由类加载器完成,java设计团队为该类加载器赋予了灵活可扩展的属性,不同的类加载器加载出来的java类是不相等的.

java提供了三种类加载器类:启动类加载器(BootStrap ClassLoader,由c++编写),扩展类加载器(Extension ClassLoader,java编写,可以加载制定路径下的类文件),系统类加载器(Application ClassLoader,java编写,默认的加载器,加载classPath上的类).

双亲委派模型

三种加载器的父子关系为:启动类加载器->扩展类加载器->系统类加载器,子类加载器收到请求的时候,不做处理,上传父类处理,当父类反馈无法处理抛出异常的时候,才尝试自己处理

这种模型可以体现加载器的优先级,并且不会出现加载多次的情况

用户自己实现加载器的话,如果继承ClassLoader类,需要重写findClass(String name)方法,如果系统类加载器父类加载失败,会调用findClass()完成加载

2.验证

验证主要验证文件格式,java语言规范,验证程序语义的合法性,如果确定class文件没有问题,可以-Xverify:none关闭类加载的验证阶段,以提高加载速度.

3.准备

为静态变量分配内存和设定初始值.

4.解析

将常量池内的符号引用替换为直接引用,解析的符号引用主要为代码中的:1.类或接口;2.字段(可能表示的某类和某接口);3.类方法;4.接口方法.

5.初始化

先清除内存中的数据为0,然后按照代码的要求为类付初始值.

二.字节码的执行

class字节码在执行一个方法的时候,会生成自己的运行时栈,栈大体由四部分组成,来实现方法的运行

1.局部变量表

保存基础数据类型,包括指向性的数据类型reference(找到堆中的类内存数据和方法区中的类信息数据),用于数据的访问.

2.操作数栈

在执行代码时会执行jvm中的字节码指令,有些指令码需要有栈做配合做计算,这时就用到了操作数栈.

3.动态链接

在运行阶段由符号引用转化来的直接引用保存在改栈区.

4.方法返回地址

方法执行结束后需要返回执行该方法的初始位置,改栈区负责记录方法的返回位置.

猜你喜欢

转载自blog.csdn.net/l450741881/article/details/88131774