深入理解Java虚拟机系列笔记

类加载过程

最近开始学习Java虚拟机,今天学习了类加载的三个过程,遂写一篇博客作为学习笔记

类加载子系统概述
类加载子系统作为JVM的一部分,负责将硬盘中的class字节码文件加载到JVM中。类加载器只负责将类加载到JVM中,不保证程序一定可以正确执行,决定程序是否可以正常运行的是执行引擎。
类被加载后存储于方法区中。方法区中的内容除了类的相关信息之外,还包括运行时常量池、字符串字面量及数字常量等。

上图的几点说明
1、class存储于硬盘中
2、字节码文件加载到JVM中,存放在方法区,被称为DNA元数据模板
3、在“.class文件->JVM->DNA元数据模板”这一过程中,类加载器起到了运输工具的作用

类的加载过程

类的加载共分为三部分
第一部分:Loading(加载)
1、通过类的全名获取该类的二进制字节流
类的全名是指带包名的类名,如java.lang.String , java.util.Date等
2、将字节流所代表的静态存储结构转化为方法区的运行时数据结构
3、在内存中生成一个代表这个类的java.lang.Class对象,作为方法区这个类的各种数据访问入口

第二部分:Linking(链接)
链接部分共分成3步:验证、准备、解析
验证:确保class文件中的信息的正确性,防止危害到Java虚拟机。因为字节码文件本质上还是二进制方式存储的,用户也可以从键盘上任意捏造字节码文件,显然这样的字节码文件是不合法的,甚至会恶意攻击、篡改其他文件甚至破坏虚拟机,因此验证这一步不可或缺。能被Java虚拟机识别的class文件都以"CAFEBABE"开头

准备:为类变量分配内存并设置该类变量初始值
关于准备过程的几点注意事项:
①这里不包含用final修饰的static,因为final在编译阶段就分配好内存了,准备阶段会显示初始化
②这里不会为实例变量分配初始化,因为实例变量是在new对象时分配到堆区的,而类变量位于方法区
③总之,准备阶段只会为没有final修饰的static变量分配内存并初始化
④分配初始值是变量类型对应的初始值,如int默认值为0.boolean默认值为false等

解析:将常量池内的符号引用转换为直接引用

第三部分:初始化
初始化阶段执行类构造器方法(),这个方法不需要我们自己定义,只要这个类中存在静态变量、静态代码块,这个方法编译器会自动生成。
()方法中的指令执行顺序按照源文件中出现的顺序执行
要特别注意这里可能会出现的前向引用错误,比如下面的代码在IDEA中编译时会自动报错:

虽然类变量a在链接阶段的准备过程就已经分配好了内存,但
()方法中的代码顺序为:先执行static代码块,再执行为类变量a赋值1,因此会导致前向引用错误

public static void main(String[] args){static{System.out.println(a); //错误,前向引用报错}private static int a = 1;}

另外还要特别注意:()方法不同于类的构造器。每一个类都会有构造器,但不一定会有()方法,比如下面的类A没有()方法而类B就有

class A{public static void main(String[] args){}}class B{ public static int a = 1;  public static void main(String[] args){    }}

同时,如果该类具有父类,Java虚拟机会保证父类的()方法执行完后再执行子类的()方法

来源:https://www.icode9.com/content-1-852301.html

(0)

相关推荐

  • 周末请看:2万字!JVM核心知识总结,赠送18连环炮

    回复"000"获取大量电子书 作为java开发人员,JVM是必备的,今天,我把JVM的核心知识点进行了一个总结,画了一张思维导图. 图展开太了,需要的加我微信tj20120622, ...

  • Jvm基础,快进来复习复习吧~

    大家好,今天总结了一下老生常谈的 JVM,这也是面试必问的知识. 话不多说,整起来!! 1.JVM 是什么? 1.Java 虚拟机(Jvm)是可运行 Java 代码的假想计算机. 2.Jvm 充当着一 ...

  • JVM真香系列:轻松理解class文件到虚拟机(上)

    回复"000"获取大量电子书 JVM初探 class文件到JVM中,就相当于我们吃饭,食物吃进了肚子里,不同的营养成分被身体不同的器官吸收. 查找class文件并导入到JVM中 ( ...

  • JVM-类加载

    JVM 类加载 JVM整个流程图 一个java文件被编译为class文件后,剩下的操作都交给jvm来执行,其中第一步就是将class文件加载到jvm,而这一步就是由类加载器来完成的 类加载的流程又分为 ...

  • 《深入理解Java虚拟机》 Java对象的生命周期

    Java虚拟机运行时数据区 方法区:存储 类信息.常量.静态变量.即使编译器编译后的代码等数据,也有别名叫做非堆.  方法区其中有包含有 运行时常量池,用于存放编译期生成的各种字面量和符号引用.其中, ...

  • 深入理解Java虚拟机 &GC分代年龄

    转自:https://www.cnblogs.com/xiarongjin/p/8309839.html 堆内存 Java 中的堆是 JVM 所管理的最大的一块内存空间,主要用于存放各种类的实例对象. ...

  • 深入理解java虚拟机

    本博客所有内容为阅读<深入理解java虚拟机>小结,如有侵权,请联系删除. 运行时数据区域 线程共享的数据区 堆 对于java应用程序来说,堆是虚拟机所管理的内存中最大的一块.虚拟机启动时 ...

  • JAVA多线程学习笔记整理

    多线程: 三种创建方法 继承Thread类,以线程运行内容重写run方法,创建Thread对象并用start方法启动该线程. (匿名内部类) (Lambda表达式) 实现Runable接口,以线程运行 ...

  • 2021最新 Java虚拟机(JVM)面试题精选(附刷题小程序)

    推荐使用小程序阅读 为了能让您更加方便的阅读 本文所有的面试题目均已整理至小程序<面试手册> 可以通过微信扫描(或长按)下图的二维码享受更好的阅读体验! 目录 推荐使用小程序阅读 1. J ...

  • 最简单直接地理解Java软件设计原则之里氏替换原则

    理论性知识 定义 里氏替换原则,Liskov Substitution principle(LSP). 抽象定义是下面这样的 如果对每一个类型为T1的对象O1,都有类型为T2的对象O2,使得以T1定义 ...

  • Java跨平台原理与Java虚拟机(JVM)

    Java跨平台原理(字节码文件.虚拟机) C/C++语言都直接编译成针对特定平台机器码.如果要跨平台,需要使用相应的编译器重新编译. Java源程序(.java)要先编译成与平台无关的字节码文件(.c ...

  • 28次面试从未被拒,只因学习了阿里大牛写的这份Java技术成长笔记

    阿里使用的技术一直都走在前沿,程序员所学和所掌握的也一直以阿里等一线互联网企业的要求为标准,所以阿里需要什么样的人才,成为了很多程序员的发展目标和学习方向. 实际上,阿里巴巴发展也离不开公司里的每一个 ...

  • 为市井存照,为药都扬名——读杨小凡药都人物系列笔记小说

    毕竟都姓杨,虽然我称杨小凡为"杨兄"有天然的优势,但抛开文学创作水平不说,仅论行政职务,称呼杨小凡为"杨兄",就有高攀的嫌疑.他有一些麾下是我的朋友,他们都亲切 ...