类从被加载到虚拟机内存中开始,到卸载出内存为止,整个生命周期:
一、类加载的时机
1. 实例化对象的时候、读取或设置一个类的静态字段的时候、调用一个类的静态方法的时候;
2. 使用java.lang.reflect包的方法对类进行反射调用的时候;
3. 当初始化一个类,发现其父类还没有进行过初始化,则需要先触发其父类初始化;
4. 当虚拟机启动时,用户需要指定一个要执行的主类,虚拟机会先初始化这个主类;
5. 当使用jdk1.7的动态语言时,
接口的初始化与类的初始化的区别:当一个类在初始化时,其父类必须全部都已经初始化过了,但是接口不一样,它不一定要其父接口全部都完成初始化,只是在真正使用到父接口的时候才让其初始化。
二、类加载的过程
1.加载:将一个类的二进制字节流代表的静态存储结构转化为方法区的运行时数据结构,相应的在内存中生成class对象,作为方法区这个类的各自数据的访问入口。具体可能的加载文件:(1)从zip中读取,如jar\ear\war(2)从网络中读取,如applet;(3)运行时计算生成,如reflect;(4)从其他文件读取,如jsp
2.验证:校验class文件的字节流中包含的信息是否符合当前虚拟机的要求
3.准备:主要是为类变量分配内存,并设置其初始值(注意:内存在方法区进行分配,变量的实际值在编译后,才可与变量关联映射上)
4.解析:主要是虚拟机将常量池的符号引用替换为直接引用
5.初始化:具体真正开始执行类中定义的Java程序代码
三、类加载器
比较两个类是否“相等”,必须这两个类是由同一个类加载器加载才有意义,否则,即使这两个类来源于同一个Class文件,被同一个虚拟机不同的类加载器加载,这两个类也是不相等的。
双亲委派模型:是一个类加载器接收到类加载请求时,首先将请求委托给父类加载器去完成,保证所有的加载请求最终都是由启动类加载器加载。避免了用户自己定义已经加载的对象,通过其它加载器加载,使得java程序会变得一片混乱。
查看java.lang.ClassLoader的loadClass()方法,逻辑:
1. 先检查是否已经被加载过
2. 如果没有加载则调用父加载器的loadClass方法
3. 如果父加载器为空则默认使用启动类加载器加载
4. 如果加载失败,抛出ClassNotFoundException异常后,再调用自己的findClass方法进行加载
protected Class<?> loadClass(String name, boolean resolve) throws ClassNotFoundException { synchronized (getClassLoadingLock(name)) { // First, check if the class has already been loaded Class<?> c = findLoadedClass(name); if (c == null) { long t0 = System.nanoTime(); try { if (parent != null) { c = parent.loadClass(name, false); } else { c = findBootstrapClassOrNull(name); } } catch (ClassNotFoundException e) { // ClassNotFoundException thrown if class not found // from the non-null parent class loader } if (c == null) { // If still not found, then invoke findClass in order // to find the class. long t1 = System.nanoTime(); c = findClass(name); // this is the defining class loader; record the stats sun.misc.PerfCounter.getParentDelegationTime().addTime(t1 - t0); sun.misc.PerfCounter.getFindClassTime().addElapsedTimeFrom(t1); sun.misc.PerfCounter.getFindClasses().increment(); } } if (resolve) { resolveClass(c); } return c; } }
破坏双亲委派模型
第一次:引入双亲委派模型,在jdk1.2时
第二次:解决某些基础类要调用回用户的代码,比如JNDI服务
第三次:解决追求程序的动态性,比如代码热替换(HotSwap)、模块热部署(Hot Deploymnet),了解osgj的类加载器能掌握类加载的精髓
相关推荐
类加载器的设计遵循双亲委派模型,它分为三个主要部分:启动类加载器、扩展类加载器和应用类加载器。 #### 二、类加载过程 类加载过程主要包括三个步骤: 1. **加载**:通过类的全限定名找到该类的二进制字节流。...
### 类加载器详解 #### 一、类加载器概述 **类加载器(ClassLoader)**是Java虚拟机(JVM)中的一个重要组成部分,它负责将编译好的`.class`文件加载到JVM中,使得这些类可以在Java环境中运行。类加载器不仅能够加载类...
1. Bootstrap ClassLoader:这是最基础的类加载器,由JVM本身实现,负责加载JRE的`<JAVA_HOME>/lib`目录下的核心类库,或者被`-Xbootclasspath`参数指定的路径中的类。 2. Extension ClassLoader:扩展类加载器,...
Java开发中的类加载器是Java运行环境的核心组件之一,它负责查找、加载和初始化类文件。在传统的Java应用中,类通常是从硬盘上的类路径(ClassPath)或模块路径(ModulePath)中加载的。然而,随着开发模式的演变,...
- Java中的类加载器采用双亲委派模型,即一个类首先由启动类加载器Bootstrap ClassLoader尝试加载,如果找不到则交给扩展类加载器Extension ClassLoader,再找不到则交由应用程序类加载器AppClassLoader,最后如果...
### 深入研究Java类加载机制 #### 一、Java类加载机制概述 Java类加载机制是Java程序运行的第一步,它对于理解Java虚拟机(JVM)的行为至关重要。类加载过程涉及到类的加载、链接(验证、准备、解析)、初始化等...
在Java编程语言中,类加载器(ClassLoader)是运行时环境的重要组成部分,它负责将类的字节码从各种来源(如硬盘、网络或内存)加载到Java虚拟机(JVM)中,使得程序能够执行。类加载工具则是辅助开发者理解和分析类...
Java 类加载原理是Java运行时环境中的核心机制之一,它涉及到类的生命周期、类加载器的层次结构以及类的查找和加载过程。了解这一机制对于深入理解Java平台的工作原理至关重要,尤其是在开发自定义类加载器或者处理...
类加载器遵循双亲委派模型,这意味着当一个类加载器尝试加载类时,它首先会将请求委托给其父类加载器,直到到达顶层的Bootstrap ClassLoader,如果父类加载器无法找到该类,子类加载器才会尝试自己加载。 在Tomcat...
Java 类加载器原理 Java 类加载器是Java虚拟机(JVM)的核心组成部分,它负责将类的字节码加载到内存中并转换为可执行的Java类。类加载器的作用不仅仅是加载类,还包括确保类的唯一性,避免重复加载,并且遵循特定...
Java 类加载机制是Java技术体系中的重要组成部分,它关乎到程序运行时的类查找与实例化。当遇到`java.lang.ClassNotFoundException`异常时,通常是因为类加载过程出现了问题。了解类加载机制对于解决这类问题至关...
在Java编程语言中,类加载器(ClassLoader)是运行时环境的一个重要组成部分,它负责将类的字节码从各种来源加载到Java虚拟机(JVM)中,从而使得程序可以执行。自定义类加载器允许开发人员根据特定需求定制加载类的...
类加载器的知识不仅仅局限于基础概念,还包括类加载的时机(静态加载、动态加载)、类加载器的实现(如自定义类加载器)、类的卸载、以及类加载器与安全策略的关系等。深入理解和掌握这些知识点,对于开发高效、安全...
### Java类加载内幕详解 #### 一、引言 在Java世界中,类加载机制是一项极为重要的技术。它不仅关乎程序的启动与运行,更是Java动态性与灵活性的基础。本文旨在深入探讨Java类加载的过程、原理及其在实际开发中的...
例如,当我们尝试加载 `java.lang.Object` 类时,首先会由启动类加载器加载,如果它找不到,会继续交给扩展类加载器,接着是系统类加载器,最后才会由用户自定义的类加载器尝试加载。 1.3 类加载双亲委派示例 为了...
类加载器是 Java 语言的一个创新,也是 Java 语言流行的重要原因之一。它使得 Java 类可以被动态加载到 Java 虚拟机中并执行。类加载器从 JDK 1.0 就出现了,最初是为了满足 Java Applet 的需要而开发出来的。Java ...
Java类加载器是Java虚拟机(JVM)的关键组成部分,它负责查找并加载类到内存中,使得程序能够运行。自定义Java类加载器允许我们根据特定需求扩展默认的加载机制,例如,从非标准位置加载类或者实现动态加载。在Java...
在Java编程中,静态代码块(Static Block)和类加载器(Class Loader)是两个重要的概念,它们在软件开发中有着广泛的应用。本案例聚焦于如何利用静态代码块结合类加载器来高效地获取资源文件,尤其是属性配置文件。...
系统类加载器在加载类时,会先尝试让扩展类加载器加载,如果扩展类加载器无法加载,则再由系统类加载器自己尝试加载。这样的设计是为了保证核心类库的唯一性和安全性,避免用户自定义的类覆盖了 JDK 内置的核心类。 ...