Java类的加载,连接和运行过程
2011-11-25 00:48
169 查看
希望大家对java的学习不用仅仅停留在api的调用上,要对内部运行机制有一定的了解。
类的加载 连接和运行
当程序主动使用某个类时,如果该类还未被加载到内存中,系统会通过加载,连接,初始化三个步骤来对该类进行初始化,JVM会完成这三个步骤,有时我们也讲这三个步骤统称为类的加载或初始化。
类的加载 类的加载是指类的class文件读入内存中,并为之创建java.lang.Class类的一个对象。也就是说当程序中使用任何的类时系统都会会值建立一个java.lang.Class类对象。这在java反射机制中会遇到。
类的连接 当类被加载后,系统为之生成一个对应地Class对象,接着将会进入连接阶段。连接阶段将会负责把类的二进制数据合并到JRE中,类的连接分为三个阶段:验证:用于验证被加载的类是否有正确的内部结构。准备:类准备阶段负责为类的静态属性分配内存,并为之设置默认初始值。解析:将类的二进制数据中的符号引用替换为直接引用。
类的初始化 在类的初始化阶段 虚拟机负责对类进行初始化,主要是对静态属性进行初始化。Java类中队静态属性指定初始值有两种方式:声明静态属性时指定初始化值;使用静态初始化块为静态属性指定初始值。
JVM初始化一个类包含如下步骤:
假如这个类还没有被加载和连接,则先加载和连接该类
假如该类有直接的父类还没有被初始化,则初始化其直接父类。
假如类中有初始化语句,则系统异常执行这些初始化语句。
下面介绍一下java中的静态初始化块
静态初始化块是类相关的。系统将在类初始化阶段执行静态初始化块,而不是在创建对象时才执行,所以静态初始化块要比普通初始化块先执行。
如下面的例子:
类的加载 连接和运行
当程序主动使用某个类时,如果该类还未被加载到内存中,系统会通过加载,连接,初始化三个步骤来对该类进行初始化,JVM会完成这三个步骤,有时我们也讲这三个步骤统称为类的加载或初始化。
类的加载 类的加载是指类的class文件读入内存中,并为之创建java.lang.Class类的一个对象。也就是说当程序中使用任何的类时系统都会会值建立一个java.lang.Class类对象。这在java反射机制中会遇到。
类的连接 当类被加载后,系统为之生成一个对应地Class对象,接着将会进入连接阶段。连接阶段将会负责把类的二进制数据合并到JRE中,类的连接分为三个阶段:验证:用于验证被加载的类是否有正确的内部结构。准备:类准备阶段负责为类的静态属性分配内存,并为之设置默认初始值。解析:将类的二进制数据中的符号引用替换为直接引用。
类的初始化 在类的初始化阶段 虚拟机负责对类进行初始化,主要是对静态属性进行初始化。Java类中队静态属性指定初始值有两种方式:声明静态属性时指定初始化值;使用静态初始化块为静态属性指定初始值。
JVM初始化一个类包含如下步骤:
假如这个类还没有被加载和连接,则先加载和连接该类
假如该类有直接的父类还没有被初始化,则初始化其直接父类。
假如类中有初始化语句,则系统异常执行这些初始化语句。
下面介绍一下java中的静态初始化块
static{ }(当Java创建一个对象时,系统先为对象的说有实例属性分配内存,当然前提是该类已经加载过。接着为这些属性初始化,其初始化的顺序为:先执行初始化块或声明属性时指定的初始值,再执行构造方法里指定的初始值)
静态初始化块是类相关的。系统将在类初始化阶段执行静态初始化块,而不是在创建对象时才执行,所以静态初始化块要比普通初始化块先执行。
如下面的例子:
class A{ static{ System.out.println("A中静态初始化块"); } { System.out.println("A中普通初始化块"); } public A(){ System.out.println("A中无参构造方法"); } } class B extends A{ static{ System.out.println("B中静态初始化块"); } { System.out.println("B中普通初始化块"); } public B(){ System.out.println("B中无参构造方法"); } public B(String msg){ this(); System.out.println("B中有参构造方法"); } class C extends B{ static{ System.out.println("C中静态初始化块"); } { System.out.println("C中普通初始化块"); } public C(){ super("xuan"); System.out.println("C中无参构造方法"); } } public class Test{ public static void main(String[] args){ new C(); new C(); } }分析:第一次创建一个C对象时,因为还未加载C类,因此需要先加载并初始化C类。初始化C类时先执行期最顶层父类的静态初始化块,再执行其直接父类的静态初始化块,最后初始化本身的静态初始化块。当C类已经初始化后,C类在JVM中会一直存在,因此第二次在创建C类对象时不再对C类进行初始化。而是对对象实例进行初始化,每次创建一个对象时都需要先执行最顶层父类的初始化块和构造方法,然后是父类的初始化块和构造方法,以此类推。最后执行自己的初始化块和构造方法。
相关文章推荐
- java类从加载、连接到初始化过程详解
- JVM运行和类加载的全过程
- JAVA虚拟机加载类到运行过程总结
- 分析Java类加载全过程
- Linux基础: 系统加载过程和运行级别含义
- 类的加载和连接过程
- JVM运行和类加载过程
- 从一道面试题来认识java类加载时机与过程
- 从一道面试题来认识java类加载时机与过程【转】
- 程序运行过程中的编译与连接阶段
- 转载:用oralce连接.net客户端出现问题:“数据连接不成功,请检查该数据库是否已启动尝试加载oracle客户端时引发BadImageFormatException.如果在安装32位Oracle客户端组件的情况下以64位模式运行,”的解
- 从一道面试题来认识java类加载时机与过程
- JAVA学习34_java类加载全过程
- java类加载机制的过程
- JVM核心之 JVM运行和类加载全过程
- Java类加载时机与过程
- Java类加载过程
- 详细解说Java类加载全过程
- Linux进程启动过程分析do_execve(可执行程序的加载和运行)---Linux进程的管理与调度(十一)
- 【JVM】类加载、连接和初始化过程