JVM原理之类加载的全过程

 更新时间:2025年01月08日 09:29:14   作者:mikey棒棒棒  
文章详细介绍了Java类加载过程,包括加载、链接、初始化、使用和卸载五个阶段,并解释了符号引用和直接引用的区别,以及类变量和实例变量的区别,此外,还介绍了Class.forName()方法的作用和使用场景

JVM原理-类加载过程

Java类加载过程

可以看作是将我们写的代码(以class文件的形式)转化为可以运行的程序。

这过程分为几个步骤:加载、链接、初始化、使用和卸载。

1.加载:找到并打开书

  • 过程:从书架上找到你要的书,把它拿到桌子上,准备阅读。
  • 对应Java的过程:JVM从硬盘上找到编译好的class文件(如Dog.class),然后把它读入内存里,生成一个Class对象。
  • Class对象:这个对象包含了类的各种信息,比如类名、方法、字段等,相当于一本被打开的书。

2. 链接:检查书的内容和准备好工具

链接阶段包括验证、准备和解析三个步骤:

验证:检查书里的内容是否有错误。

  • 对应Java的过程:检查class文件的格式和内容是否合法,确保没有语法错误或其他问题。
  • 如果有错误,程序会抛出异常,无法继续运行。

准备:为静态变量分配内存并初始化为默认值。

  • 对应Java的过程:静态变量在这个阶段被分配内存,并初始化为默认值。
  • 例如,static int a;会被初始化为0。

解析(可选):把间接引用转换为直接引用。

  • 对应Java的过程:把符号引用(指向类、方法、字段的字符串)
  • 转换为直接引用(内存地址),方便后续快速访问。

3. 初始化:翻开书并开始阅读

过程:正式开始根据书里的内容进行设置和操作。

对应Java的过程:执行类的初始化,包括:

  • 静态变量的赋值:将静态变量赋值为代码中定义的值。例如,static int a = 10;,此时a会被设置为10。
  • 静态代码块的执行:依次执行静态代码块中的代码。静态代码块可以用于复杂的初始化工作。
  • 顺序:静态变量和静态代码块的初始化按照它们在代码中出现的顺序进行。

4. 使用:开始利用书中的信息

  • 过程:根据书中的指导完成具体任务。
  • 对应Java的过程:实际使用类和对象,包括创建实例和调用方法。
  • 对象创建:如new Dog(),JVM会在堆内存中为Dog对象分配空间。

步骤:

  1. 分配内存:为新对象分配内存。
  2. 设置默认值:对象的属性被初始化为默认值(如数字为0,对象引用为null)。
  3. 执行初始化代码:按照代码中定义的顺序为属性赋值。
  4. 执行构造函数:运行构造函数,进行进一步初始化和操作。

5. 卸载:书用完后放回书架

  • 过程:书看完了,把它合上,放回书架,不再需要它了。
  • 对应Java的过程:当类不再需要时,JVM会把类从内存中卸载,释放占用的资源。
  • 垃圾回收:JVM的垃圾回收机制会自动检测不再使用的类和对象,并回收它们占用的内存。

对类初始化的5种情况

根据JVM规范,类初始化的情况有且只有以下5种:

  1. 创建类的实例:当我们用new来创建类的对象时,比如new Dog(),如果这个类还没有被初始化,那么它必须先初始化才能创建对象。
  2. 调用类的静态方法:比如Dog.bark(),静态方法属于类本身而不是某个对象,因此在调用时,类必须先初始化。
  3. 访问类或接口的静态变量:当我们访问类的静态变量时,比如Dog.age,这也会导致类的初始化。
  4. 使用Class.forName()方法:这种方法会强制初始化一个类。比如Class.forName("Dog")会让Dog类被加载并初始化。
  5. 类加载器启动主类:当我们运行一个程序时,比如执行java DogMain,JVM会先初始化DogMain类并执行它的main方法。

符号引用和直接引用的区别是什么?

  • 符号引用:可以理解为一种间接的引用,它并不指向内存中的具体位置。相当于书里提到了某个章节,但没有告诉你具体在哪一页。
  • 直接引用:是内存中的具体地址,也就是可以直接找到的目标地址。相当于书里直接标明某个章节在第几页。

类变量和实例变量

类变量(静态变量)

  • 定义:使用static关键字修饰的变量。
  • 归属:属于类本身,而不是某个特定的对象。
  • 共享性:所有实例共享同一个类变量。如果一个实例修改了类变量的值,其他实例也会看到这个变化。
  • 生命周期:在类加载时被初始化,直到类卸载时被回收。其存储在方法区(Method Area)。
  • 访问方式:可以通过类名直接访问,也可以通过实例访问,但推荐使用类名进行访问。

实例变量

  • 定义:没有使用static关键字修饰的变量。
  • 归属:属于类的每个实例,每个实例都有自己独立的一份实例变量。
  • 独立性:每个实例的实例变量相互独立,一个实例的实例变量变化不会影响其他实例的实例变量。
  • 生命周期:在对象创建时被初始化,直到对象被垃圾回收时被回收。其存储在堆内存(Heap Memory)。
  • 访问方式:只能通过对象实例来访问,不能通过类名直接访问。

Class.forName()

Class.forName()的主要作用是 动态加载类,尤其是在需要根据类名字符串来加载类的情况下(比如 JDBC 驱动程序、反射等)。

这提供了一种灵活的方式,允许你在运行时加载类,而不是在编译时绑定类。

当你调用这个方法时,JVM 会尝试根据你传递的类名(作为字符串)加载该类,并且会执行该类的静态代码块(如果有的话)。

总结

以上为个人经验,希望能给大家一个参考,也希望大家多多支持脚本之家。

相关文章

  • Spring实战之容器后处理器操作示例

    Spring实战之容器后处理器操作示例

    这篇文章主要介绍了Spring实战之容器后处理器操作,结合实例形式分析了spring容器后处理器配置、使用操作技巧与相关注意事项,需要的朋友可以参考下
    2019-12-12
  • Spring Cloud Gateway编码实现任意地址跳转的示例

    Spring Cloud Gateway编码实现任意地址跳转的示例

    本文主要介绍了Spring Cloud Gateway编码实现任意地址跳转的示例,文中通过示例代码介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2021-12-12
  • IntelliJ IDEA 中必有得插件和配置

    IntelliJ IDEA 中必有得插件和配置

    这篇文章主要介绍了IntelliJ IDEA 中必有得插件和配置,本文通过图文并茂的形式给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友可以参考下
    2020-05-05
  • 详解Spring Bean的集合注入和自动装配

    详解Spring Bean的集合注入和自动装配

    这篇文章主要为大家详细介绍了Spring Bean中集合注入和自动装配的方法,文中的示例代码讲解详细,对我们学习有一定的帮助,需要的可以参考一下
    2022-06-06
  • Mybatis Interceptor线程安全引发的bug问题

    Mybatis Interceptor线程安全引发的bug问题

    这篇文章主要介绍了Mybatis Interceptor线程安全引发的bug问题及解决,具有很好的参考价值,希望对大家有所帮助。如有错误或未考虑完全的地方,望不吝赐教
    2023-02-02
  • java自定义异常打印内容详解

    java自定义异常打印内容详解

    这篇文章主要为大家详细介绍了java自定义异常打印内容的相关资料,文中示例代码介绍的非常详细,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2019-10-10
  • SpringBoot自定义注解验证枚举的实现

    SpringBoot自定义注解验证枚举的实现

    本文主要介绍了SpringBoot自定义注解验证枚举的实现,数据校验,需要对枚举类型的数据传参,进行数据校验,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧
    2024-01-01
  • mybatis-plus多表关联查询功能的实现

    mybatis-plus多表关联查询功能的实现

    本文给大家介绍mybatis-plus多表关联查询功能的实现代码,本文通过实例代码给大家介绍的非常详细,对大家的学习或工作具有一定的参考借鉴价值,需要的朋友参考下吧
    2021-11-11
  • SpringBoot项目使用yml文件链接数据库异常问题解决方案

    SpringBoot项目使用yml文件链接数据库异常问题解决方案

    在使用SpringBoot时,利用yml进行数据库连接配置需小心数据类型区分,如果用户名或密码是数字,必须用双引号包裹以识别为字符串,避免连接错误,特殊字符密码也应用引号包裹
    2024-10-10
  • Java实现文件和base64流的相互转换功能示例

    Java实现文件和base64流的相互转换功能示例

    这篇文章主要介绍了Java实现文件和base64流的相互转换功能,涉及Java文件读取及base64 转换相关操作技巧,需要的朋友可以参考下
    2018-05-05

最新评论