类的加载时指将类的.class文件中的二进制数据读取到内存中,将其存放在运行时数据区的方法区,然后在堆区创建一个java.lang.Class对象,用来封装类在方法区的数据结构
java虚拟机与程序的生命周期
在如下几张情况,java虚拟机讲结束生命周期
1.执行了System.exit()方法
2.程序正常执行结束
3.程序在执行过程中遇到异常或错误终止
4.由于操作系统出现错误而导致java程序终止
加载:查找并加载类的二进制数据
连接:
1.验证:确保被加载的类的正确性
2.准备:为类的静态变量分配内存,并将其转化为默认值
3.解析:把类中的符号引用转换为直接引用
初始化:为类的静态变量赋予争取的初始值
Java程序对类的使用方式可以分为两种
1.主动使用
2.被动使用
所有的java虚拟机实现必须在每个类或者接口被java程序“首次主动使用”才初始化他们
主动使用(六种)
1.创建类的实例
2.访问某个类或者接口的静态变量,或者对该静态变量赋值
3.调用类的静态方法
4.反射(如Class.forName(“com.xxx.xx”)
5.初始化一个类的子类
6.java虚拟机启动时被标明为启动类的(Java Test)
类加载的最终产品是位于堆区的Class对象
Class对象封装了类在方法区的数据结构,并向Java程序员提供了访问方法内的数据结构的接口
有两种类型的类加载器
1.java虚拟机自带的加载器
1.1根类加载器(Bootstrap) (c++实现的)
1.2扩展类加载器(Extension) (使用java代码实现)
1.3系统类加载器(s使用java代码实现)
用户自定义的类加载器
.java.lang.ClassLoader的子类
用户可以定制类的加载方式
package com.xxf.reflect.classloader;
public class ClassloaderTest {
public static void main(String[] args) throws Exception
{
Class clasz=Class.forName(String.class.getName());
System.out.println(clasz.getClassLoader());
System.out.println(Class.forName(ClassloaderTest.class.getName()).getClassLoader());
}
}
运行结果:
null
sun.misc.Launcher$AppClassLoader@18b4aac2
Process finished with exit code 0
AppClassLoader是Classloader的子类,验证了用户自定义类的类加载器都是classloader的子类