java学习:类的加载机制

jvm 一行代码是怎么运行的:

首先,java代码会被编译成字节码,字节码就是java虚拟机定义的一种编码格式,需要java虚拟机才能够解析,java虚拟机需要将字节码转换成机器码才能在cpu上执行。

jvm如何加载一个类:

第一步:加载,双亲委派:启动类加载器(jre/lib),系统扩展类加载器(ext/lib),应用类加载器(classpath),前者为c++编写,所以系统加载器的parent为空,后面两个类加载器都是通过启动类加载器加载完成后才能使用。加载的过程就是查找字节流,可以通过网络,也可以自己在代码生成,也可以来源一个jar包。另外,同一个类,被不同的类加载器加载,那么他们将不是同一个类,java中通过类加载器和类的名称来界定唯一,所以我们可以在一个应用成存在多个同名的类的不同实现。

第二步:链接:(验证,准备,解析) 验证主要是校验字节码是否符合约束条件,一般在字节码注入的时候关注的比较多。准备:给静态字段分配内存,但是不会初始化,解析主要是为了将符号引用转换为实际引用,可能会触发方法中引用的类的加载。

第三步:初始化,如果赋值的静态变量是基础类型或者字符串并且是final的话,该字段将被标记为常量池字段,另外静态变量的赋值和静态代码块,将被放在一个叫cinit的方法内被执行,为了保证cinit方法只会被执行一次,这个方法会加锁,我们一般实现单例模式的时候为保证线程安全,会利用类的初始化上的锁。 初始化只有在特定条件下才会被触发,例如new 一个对象,反射被调用,静态方法被调用等。

推荐阅读更多精彩内容