Java中Class.forName和ClassLoader.loadClass的比较

23 篇文章 0 订阅

一个类型从被加载到虚拟机内存中开始,到卸载出内存为止,它的整个生命周期将会经历加载(Loading)验证(Verification)准备(Preparation)解析(Resolution)初始化(Initialization)使用(Using)卸载(Unloading)七个阶段,其中验证、准备、解析三个部分统称为连接(Linking)
  加载、验证、准备、初始化和卸载这五个阶段的顺序是确定的,类型的加载过程必须按照这种顺序按部就班地开始,而解析阶段则不一定:它在某些情况下可以在初始化阶段之后再开始,这是为了支持Java语言的运行时绑定特性(也称为动态绑定或晚期绑定)。这里说的是按部就班地“开始”,而不是按部就班地“进行”或按部就班地“完成”,强调这点是因为这些阶段通常都是通常都是互相交叉混合进行的,会在一个阶段执行的过程中调用、激活另一个阶段
------上面是引用《深入理解Java虚拟机》中的两段话。

下面大致说下各阶段干了些什么:
加载:查找和导入类或接口的二进制数据;
验证:检查导入类或接口的二进制数据的正确性;
准备:给类的静态变量分配并初始化存储空间;
解析:将符号引用转成直接引用;
初始化:激活初始化类中的所有类变量的赋值动作和静态语句块(static{})中的语句块(初始化阶段实际就是执行类构造器<clinit>()方法的过程);
使用:对象实例化,垃圾收集,对象终结等动作;
卸载:在jvm中卸载类。
类加载过程便是加载(Loading)、验证(Verification)、准备(Preparation)、解析(Resolution)、初始化(Initialization)这五个过程。

1.Class.forName
实际调用的是Class类中下面的静态方法:
public static Class<?> forName(String name, boolean initialize, ClassLoader loader) throws ClassNotFoundException{}
参数的含义:
name:所需类的完全限定名
initialize:类是否要初始化(true-类将被初始化,false-类不被初始化)
loader:指定的ClassLoader(类加载器)

2.ClassLoader.loadClass
实际调用的是ClassLoader类中下面的方法:
protected Class<?> loadClass(String name, boolean resolve) throws ClassNotFoundException{}
参数的含义:
name:类名
resolve:是否解析该类

总结:
  Class.forName方法执行之后(initialize=true–初始化完成了)已经对被加载类的静态变量分配完了存储空间; ClassLoader.loadClass方法由于解析阶段可能在初始化后也可能在初始化之前,所以不一定对被加载类的静态变量分配完了存储空间。
  如果想要在加载一个类的时候初始化静态变量等推荐用Class.forName方法。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值