Salmon的全栈知识 Salmon的全栈知识
首页
  • JavaSE
  • JavaWeb
  • Spring生态
  • JUC
  • JVM
  • Netty
  • Java各版本特性
  • 23种设计模式
  • Maven
  • Java常用框架
  • Dubbo
  • OpenFeign
  • Nacos
  • Zookeeper
  • Sentinel
  • Seata
  • Gateway
  • Go基础
  • Gin
  • SQL数据库

    • MySQL
    • Oracle
  • NoSQL数据库

    • Redis
    • MongoDB
    • ElasticSearch
  • 消息中间件

    • RabbitMQ
    • RocketMQ
    • Kafka
    • ActiveMQ
    • MQTT
    • NATS
  • 网关中间件

    • Nginx
  • Linux
  • Docker
  • Git
  • K8s
  • Solidity
  • Java
  • 计算机网络
  • 操作系统
GitHub (opens new window)
首页
  • JavaSE
  • JavaWeb
  • Spring生态
  • JUC
  • JVM
  • Netty
  • Java各版本特性
  • 23种设计模式
  • Maven
  • Java常用框架
  • Dubbo
  • OpenFeign
  • Nacos
  • Zookeeper
  • Sentinel
  • Seata
  • Gateway
  • Go基础
  • Gin
  • SQL数据库

    • MySQL
    • Oracle
  • NoSQL数据库

    • Redis
    • MongoDB
    • ElasticSearch
  • 消息中间件

    • RabbitMQ
    • RocketMQ
    • Kafka
    • ActiveMQ
    • MQTT
    • NATS
  • 网关中间件

    • Nginx
  • Linux
  • Docker
  • Git
  • K8s
  • Solidity
  • Java
  • 计算机网络
  • 操作系统
GitHub (opens new window)
npm

(进入注册为作者充电)

  • JVM基础

    • 初识JVM
    • 字节码文件详解
    • 运行时数据区
    • 垃圾回收
  • JVM实战

    • 内存调优
    • GC调优
    • 性能调优
  • JVM高级

    • GraalVM
    • 新一代的GC
    • 揭秘Java工具
  • JVM原理

    • 栈上的数据存储
    • 对象在堆上是如何存储的?
    • 方法调用的原理
    • 异常捕获的原理
    • JIT即时编译器
    • 垃圾回收器原理
  • JVM面试

    • 什么是JVM?
    • 了解过字节码文件的组成吗?
    • 说一下运行时数据区
    • 哪些区域会出现内存溢出,会有什么现象?
    • JVM在JDK6-8之间在内存区域上有什么不同
    • 类的生命周期
    • 什么是类加载器?
    • 什么是双亲委派机制
      • 双亲委派机制有什么用?
      • 总结
    • 如何打破双亲委派机制
    • Tomcat的自定义类加载器
    • 如何判断堆上的对象没有被引用??
    • JVM 中都有哪些引用类型?
    • ThreadLocal中为什么要使用弱引用?
    • 有哪些常见的垃圾回收算法?
    • 有哪些常用的垃圾回收器?
    • 如何解决内存泄漏问题?
    • 常见的JVM参数?
  • 《JVM》笔记
  • JVM面试
Salmon
2024-03-12
目录

什么是双亲委派机制

  • 关联课程内容

    • 基础篇-双亲委派机制
    • 基础篇-打破双亲委派机制
  • 回答路径

    • 类加载器和父类加载器
    • 什么是双亲委派机制
    • 双亲委派机制的作用

类加载有层级关系,上一级称之为下一级的父类加载器。

img

测试代码:

package q4classloader;



import javax.script.ScriptEngineManager;
import javax.script.ScriptException;

public class PrintParentClassLoader {
    public static void main(String[] args) throws ScriptException {
        new ScriptEngineManager();
        //扩展类加载器的父类加载器
        System.out.println(ScriptEngineManager.class.getClassLoader().getParent());
        //应用程序类加载器的父类加载器
        System.out.println(PrintParentClassLoader.class.getClassLoader().getParent());
        //自定义类加载器的父类加载器
        System.out.println(new MyClassLoader().getParent());
    }
}

打印结果:

img

  • 扩展类加载器的父类加载器但是在java中无法获得,所以打印null
  • 应用程序类加载器的父类加载器是扩展类加载器(平台类加载器)
  • 自定义类加载器的父类加载器是应用程序类加载器

双亲委派机制指的是:当一个类加载器接收到加载类的任务时,会向上查找是否加载过,再由顶向下进行加载。

img

每个类加载器都有一个父类加载器,在类加载的过程中,每个类加载器都会先检查是否已经加载了该类,如果已经加载则直接返回,否则会将加载请求委派给父类加载器。

应用程序类加载器接收到加载类的任务,首先先检查自己有没有加载过:

img

没有加载过就一层一层向上传递,都检查下自己有没有加载过这个类:

img

到了启动类加载器发现已经加载过,就返回。

另一个案例:com.itheima.my.C 这个类在当前程序的classpath中,看看是如何加载的。

先由应用程序类加载器检查,发现没有加载过,向上传递检查发现都没有加载过。此时启动类加载器会优先加载:

img

接下来向下传递加载:

img

最后由应用程序类加载器加载成功:

img

# 双亲委派机制有什么用?

1.保证类加载的安全性,通过双亲委派机制避免恶意代码替换JDK中的核心类库,比如java.lang.String,确保核心类库的完整性和安全性。

2.避免重复加载,双亲委派机制可以避免同一个类被多次加载。

# 总结

双亲委派机制指的是:当一个类加载器接收到加载类的任务时,会向上交给父类加载器查找是否加载过,再由顶向下进行加载。

双亲委派机制的作用:保证类加载的安全性,避免重复加载。

img

上次更新: 2025/03/09, 18:29:07
什么是类加载器?
如何打破双亲委派机制

← 什么是类加载器? 如何打破双亲委派机制→

Theme by Vdoing | Copyright © 2022-2025 Salmon's Blog
  • 跟随系统
  • 浅色模式
  • 深色模式
  • 阅读模式