classloader in java 本身就是一个 class 那么谁来加载 classloader class?

classloader in java is a class itself then who will load the classloader class?

ClassJava中的加载器是一个class,用于加载Java中的class个文件。

java.lang.ClassLoader是一个摘要class

我的问题是这个 java.lang.ClassLoader class 是否与 JVM 的 classloaders(1. Bootstrap class loader 2. Extensions 相关class加载器3.系统class加载器)?

或者这个 java.lang.ClassLoader 是一个单独的 class,可用于创建自定义 classloader?

Class 加载程序是 Java 运行时环境的一部分,它动态地将 Java classes 加载到 Java 虚拟机中。它负责定位库,读取那里的内容并加载库中包含的 classes 当 JVM 启动时,使用三个 class 加载器

  1. Bootstrap class 装载机

  2. 扩展程序class加载器

  3. 系统class加载器

Bootstrap class 加载程序加载核心 java 库。它是用本机代码编写的。 bootstrap class 加载器负责将 java class 之类的键和其他运行时代码加载到内存中。运行时 classes 打包在 jre/lib/rt.jar 文件中。

Extensions class 加载程序加载扩展目录中的代码。由ExtClassLoaderclass.

实现

System class 加载程序在 java.class.path 上找到的代码映射到系统 class 路径变量。它由AppClassLoaderclass实现。默认情况下,所有用户 classes 都由系统 class 加载器加载。

Java Class加载器是分层的,每当提出加载一个 class 的请求时,它都会将它委托给它的父级,这样在运行时环境中保持唯一性.如果父 class 加载器没有找到 class 那么 class 加载器本身会尝试加载 class.

所以这意味着第一个系统 class 加载器将请求委托给扩展 class 加载器,扩展 class 加载器将请求委托给 Bootstrap class 加载器将搜索 class 如果未找到,则扩展 class 加载程序将搜索 class 如果未找到,则系统 class 加载程序将搜索 class 如果未找到则它抛出 ClassNotFoundException

JVM 是否总是以系统 class 加载程序启动以加载 class?

如有错误请指正

术语“System class loader”用词不当。正如您正确指出的那样,它负责从 class 路径的位置加载 classes,即 application classes.

从 Java 8 开始,AppClassLoaderExtClassLoader 都是 java.net.URLClassLoader 的子class,后者是 [=53] 的子class =] of java.security.SecureClassLoader,它是 java.lang.ClassLoader 的子 class。所有这些 classes 都由 Bootstrap 加载程序加载,解决了先有鸡还是先有蛋的问题。

每个运行时 class 都有一个 定义 class 加载程序 。对于启动期间由 Bootstrap 加载程序定义的那些 classes,定义的 class 加载程序是 Bootstrap 加载程序。当 JVM 初始化完成并尝试启动应用程序时,应用程序 class 加载器(又名系统 class 加载器)将查询主 class。 Application class 加载器将遵循标准委托模型,首先查询父级,Extension class 加载器也是如此,并且 class 加载器将创建 class 将是 class' 定义 class 加载程序。

现在,当解析另一个 class 引用的 class 或调用 Class.forName(String) 时,包含引用的 class 的定义加载器将用于解决 class。因此,当应用程序 class 加载器加载了您的 class myapp.foo.Bar 并且它包含对 javax.swing.JButton 的引用时,它定义了 class 加载器,即应用程序 class 加载器,将被查询 class,遵循委托模型以 Bootstrap 加载器定义的 javax.swing.JButton 结束。因此 javax.swing.JButton 中的 class 引用仅通过 Bootstrap 加载程序解析,这意味着 javax.swing.JButton 不能包含对您的 myapp.foo.Bar class 的引用,因为它不在范围内。

因此,JVM 而不是 总是以“系统 class 加载程序”启动来加载 class,但仅用于解析由它(或子加载器)定义的 class 的 class 引用,或者当被显式查询时,比如解析主要 class.

有第 3 方 class 加载器不严格遵循双亲委派模型,但无论他们如何委托以及委托给哪个加载器,每个 class 都会有一个定义加载器(第一个由 getClassLoader() 返回),它将用于解析 class 中的引用。 JVM 确保一个 class 中的相同符号名称始终解析为相同的运行时 class,而不管特定的 class 加载程序如何实现查找。

请注意,在 Java 9 中,扩展 class 加载器已被平台 class 加载器取代。这个 class 加载器可能会偏离简单的父委托,即它可能会委托给应用程序 class 加载器来加载应用程序提供的模块,这些模块取代了平台提供的模块。此外,内置 class 加载器不再是 URLClassLoader 的子class。