当前位置: 首页 > ai >正文

Java类加载器与双亲委派模型深度解析

一、类加载器核心概念

类加载器是JVM的核心组件,负责通过类的权限定名获取该类的二进制字节流。它在Java虚拟机外部实现,让应用程序能自行决定获取类数据的方式。

二、四种类加载器详解

加载器类型加载路径特点获取方式
启动类加载器JAVA_HOME/lib目录加载核心类库(如rt.jar)由C++实现,Java无法直接引用
扩展类加载器JAVA_HOME/lib/ext目录加载Java扩展库ExtensionClassLoader实例
系统类加载器CLASSPATH环境变量加载应用级类库ClassLoader.getSystemClassLoader()
自定义类加载器开发者指定路径实现特殊加载需求继承java.lang.ClassLoader

三、双亲委派模型机制图解

工作流程:
  1. 委派阶段
    当类加载请求发生时,子加载器不会立即加载:

    • 系统加载器先将请求委派给扩展加载器
    • 扩展加载器继续委派给启动加载器
  2. 检查阶段

    • 启动加载器检查能否加载(核心库)
    • 扩展加载器检查能否加载(扩展库)
    • 系统加载器检查能否加载(应用类路径)
  3. 反馈阶段
    若父加载器无法加载:

    • 启动加载器 → 通知扩展加载器
    • 扩展加载器 → 通知系统加载器
    • 系统加载器 → 通知自定义加载器
  4. 加载阶段
    最终由能够加载的最底层加载器完成类加载

四、双亲委派模型三大优势

  1. 安全性保障
    防止核心API被篡改(如自定义java.lang.String类会被启动加载器优先加载)

  2. 避免重复加载
    确保类在JVM中的唯一性,当父加载器已加载时,子加载器不会重复加载

  3. 资源高效利用
    减少不必要的类加载操作,优化内存使用:

    // 验证类加载器示例
    public class LoaderDemo {public static void main(String[] args) {System.out.println(String.class.getClassLoader()); // null(启动加载器)System.out.println(LoaderDemo.class.getClassLoader()); // sun.misc.Launcher$AppClassLoader@xxxxxx(系统加载器)}
    }
    

五、打破双亲委派的场景

虽然双亲委派是默认机制,但在特定场景需要打破:

  • 热部署:OSGi框架实现模块热替换
  • SPI机制:JDBC驱动加载(使用线程上下文加载器)
  • 容器隔离:Tomcat为每个Web应用单独设置加载器
// 自定义类加载器示例
public class CustomClassLoader extends ClassLoader {@Overrideprotected Class<?> findClass(String name) {// 1. 从指定位置读取字节码// 2. 调用defineClass()方法生成Class对象return super.findClass(name);}
}

关键认知:双亲委派不是继承关系,而是组合关系。每个ClassLoader实例都持有parent引用(启动加载器的parent为null)

理解类加载机制和双亲委派模型,是掌握Java动态扩展、模块化开发和安全管理的基石。这种精巧的设计既保证了系统稳定性,又为开发者提供了灵活的扩展能力。

http://www.xdnf.cn/news/14382.html

相关文章:

  • DNS递归查询
  • BOLL指标
  • Oracle21cR3之客户端安装错误及处理方法
  • 第11章 结构 笔记
  • 华为OD-2024年E卷-小明周末爬山[200分] -- python
  • 亚马逊ASIN: B0DNTQ2YNT数据深度解析报告
  • 3.创建数据库
  • STM32103CBT6显示ST7789通过SPI方式显示柬埔寨文
  • Unity Addressable使用之入门篇
  • 讲一下进程和线程
  • Day54打卡 @浙大疏锦行
  • 37-Oracle 23 ai Shrink Tablespace(一键收缩表空间)
  • Composer 的 PHP 依赖库提交教程
  • 【Qt】Qt 基础
  • Redis-CPP通用接口
  • Leetcode 3584. Maximum Product of First and Last Elements of a Subsequence
  • 139. 单词拆分
  • (LeetCode 每日一题) 1432. 改变一个整数能得到的最大差值(贪心)
  • React组件通信——context(提供者/消费者)
  • MySQL常用函数详解之字符串函数
  • nohz_full 参数对内核软硬锁检测机制的影响分析
  • 嵌入式学习笔记 - SH79F6441 堆栈栈顶可以是片上内部RAM(00H-FFH)的任意地址怎么理解
  • (91)课113:存储函数与存储过程的区别总结。
  • DP刷题练习(三)
  • Golang 解大整数乘法
  • Python Pillow 库详解文档
  • pythton 语言的独特语法
  • Axure应用交互设计:多种类型元件实现新增中继器数据
  • 【springcloud】快速搭建一套分布式服务springcloudalibaba(五)
  • Python爬虫实战:研究Mr. Queue相关技术