JVM结构
类加载器
c1.getClassLoader();//类加载器
c1.getClassLoader().getParent();//父类加载器
APP:应用类加载器
EXC:扩展类加载器
BOOT:根类加载器
**双亲委派机制 **
-
类加载器收到加载请求
-
将这个请求向上委托给父类加载器完成,一直向上委托,直到启动类加载器
-
启动类加载器检查是否能够加载当前这个类,如果能就加载结束,不能就抛出异常,通知子类加载器
-
重复步骤,找不到就报错,ClassNotFound
![外
类加载
加载、连接、初始化
连接:验证 准备 解析
加载
生成Class对象在堆中
连接
验证:
准备:仅仅为静态类变量分配内存并且设置类变量默认初始化值** static final修饰的在编译的时候 就已经分配内存
解析:
初始化
执行类构造器<clini。t>()方法的过程,对类变量的赋值动作个静态代码块进行合并执行
当初始化一个类是发现父类没有初始化,先初始化父类
//创建对象会初始化被Class对象初始化,执行代码进行初始化
//那些会被初始化,那些不会被初始化
public class Test2 {
public static void main(String[] args) throws ClassNotFoundException {
//1.创建父类,父类Class对象被加载到方法区,并且会被Class对象初始化
//Person1 p1 = new Person1();
//2.创建子类,如果父类在之前没被加载,父类子类Class对象都会被加载到方法区
//然后会对创建对象初始化,先初始化他的父类
//Student s1 = new Student();
//3.反射也会对类初始化
//Class.forName("reflection.test1.Student");
//不会初始化
//1. 子类调用父类方法,变量,不会初始化子类(不执行子类里的代码)
//System.out.println(Student.b);
//2.数组,只是在堆中开辟空间,不会被Class类初始化
Student[] array= new Student[10];
//3.常量,常量和类变量在编译阶段都已经被初始化,所以不用初始化
System.out.println(Student.d);
}
}
class Person1{
static int b=1;
static {
System.out.println("父类初始化");
}
}
class Student extends Person1{
static int c=2;
static final int d=3;
static {
System.out.println("子类初始化");
}
}
Native、方法区
native
带navtive关键字的,说明Java的作用范围达不到了,回去调用底层C语言的库
通过本地方法调用本地接口 JNI(Java native intefac)
JNI:拓展Java的使用,适合不同的编程语言为java所用
方法区
静态变量、常量、类信息(构造方法、接口定义)、常量池
static final Class模板 常量池
栈
栈:先进先出
队列:先进先出
栈内存放:8大基本类型、对象的引用、实例方法
程序计数器
每个线程都有一个计数器,是线程私有的,是一个非常小的内存空间可以忽略不记。