JVM类加载机制

类加载运行全过程大概流程图

类加载器种类

  • 引导类加载器:加载 JRE 的 lib 目录下的核心类库。
  • 扩展类加载器:加载 JRE 的 lib 目录下 ext 目录下的 JAR 包。
  • 应用程序类加载器:加载 classpath 路径下的类,主要是加载自定义类。
  • 自定义类加载器:加载用户自定义路径下的类。

类加载器初始化

由 C++ 代码调用 Java 程序创建 Launcher 实例,这是 JVM 启动器实例,Launcher 是初始化使用了单例模式,确保一个 JVM 虚拟机内只有一个 Launcher 实例。

在 Launcher 构造方法内部,创建了扩展类加载器(ExtClassLoader)和应用程序类加载器(AppClassLoader)。

JVM 默认使用 Launcher 的 getClassLoader() 方法返回的类加载器是 AppClassLoader。

ClassLoader.loadClass() 加载类的流程

加载 >> 验证 >> 准备 >> 解析 >> 初始化 >> 使用 >> 卸载

加载: 使用类(调用类的 mian 方法,new 对象等)时才会加载,在硬盘上查找文件后,通过 IO 读取字节码文件,在加载阶段会在内存中生成一个对应的 Class 对象,作为方法区这个类的各种数据的访问入口。

验证: 校验字节码文件内容是否符合规范。

准备: 为类的静态变量分配内存,并赋予默认值。

解析: 把一些静态方法替换为指向数据所存内存的指针或句柄等。即把符号引用转化为直接引用,符号引用保存在字节码文件中,解析后的直接引用保存到 JVM 内存中。

初始化: 对类的静态变量初始化为指定的值,并执行静态代码块。

类加载的双亲委派机制


向上委托

加载某个类时一般先从应用程序类加载器加载(没有定义自定义类加载器)。

如果应用程序类加载器中已加载的类中不存在这个类,那么应用程序类加载器委托扩展类加载器。

扩展类加载器如果也没有加载过这个类,那么就委托引导类加载器。

向下委托

如果引导类加载器没有加载过这个类,并且在自己的加载路径中也找不到这个类,就把这个请求又发送回给扩展类加载器。

扩展类加载器按照同样的方式找不到把请求转发回应用程序类加载器,由应用程序类加载器加载。

为什么设计双亲委派机制

沙箱安全机制

当自己写了和核心包一样的代码,例如 java.lang.String.class,由于第一次加载需要向上委托至引导类加载器寻找这个类,引导类加载器可以寻找到,那么就加载这个类,而不会加载到自己写的类。

避免类被重复加载

子类不会再次加载父类已经加载的类。

父类意味着子类的 parent 属性值是这个父类,并不是子类继承父类的关系。

自定义类加载器

loadByte() 方法是读取本地 class 文件并把它存储到 byte[] 中。

相关推荐
稚辉君.MCA_P8_Java5 小时前
DeepSeek Java 多线程打印的19种实现方法
java·linux·jvm·后端·架构
g***78919 小时前
Java语法进阶
java·开发语言·jvm
聊天QQ:2769988511 小时前
基于MPC模型预测控制的空调加热器温度调节系统研究:融合Kalman滤波的优化算法与实现
jvm
多多*11 小时前
Threadlocal深度解析 为什么key是弱引用 value是强引用
java·开发语言·网络·jvm·网络协议·tcp/ip·mybatis
2501_9418017614 小时前
Java高性能数据库操作实战:异步任务与多线程结合代码解析
jvm
用户849137175471614 小时前
Tomcat 为什么要“造反”?深度解析 Java 类加载机制的“守”与“破”
java·jvm
杀死那个蝈坦15 小时前
UV 统计(独立访客统计)
java·jvm·spring·kafka·tomcat·maven
野生技术架构师16 小时前
Java 经典面试题汇总:多线程 +spring+JVM 调优 + 分布式 +redis+ 算法
java·jvm·spring
酷ku的森16 小时前
JVM内存结构
jvm
他们都不看好你,偏偏你最不争气16 小时前
【iOS】数据持久化
jvm·数据库·macos·ios·oracle·objective-c·cocoa