首页 > 代码库 > java类加载机制
java类加载机制
最近在重新回顾java基础,对java运行时整个内存运行的机制很好奇,看了一点深入理解java虚拟机 高级特性和最佳实践,觉得整个jvm运行机制还是比较复杂的。待日后有时间再好好深入了解,暂时先在站在理解程序的级别上简述一下。
首先先是运行时的java的内存区域
简单讲一下各个区域
程序计数器:当前线程所执行的字节码的行号指示器,循环,线程恢复等基础功能依赖这个计数器完成(线程私有,每一个线程都会有自己单独的一个计数器)。
本地方法栈:与java虚拟机栈相似,不过执行的是native方法。
方法区(包含运行时常量池):各个线程共享的区域,它用于已被虚拟机加载的类信息,常量,静态变量,即时编译器编译后的代码等数据。
java虚拟机栈:也是线程私有的,生命周期与线程相同 每个方法执行时都会创建一个栈帧(一会儿会详细讲到)结构是栈结构,先进后出。
java堆:被线程共享 java虚拟机管理的内存中最大的一块,几乎所有的对象实例都在这里分配内存,也是java垃圾收集器主要管理的区域。
运行时常量池:方法区的一部分 主要存放类的版本,字段,方法,接口等描述信息和常量池。常量池里在类加载后进入运行时常量,里面存放编译期生成的各种字面量和符号引用等。
然后就是类的加载过程
类加载时机通常在
1.new创建实例时
2.调用该类的静态方法
3.Class.forname("");
.....(当类初始化时,会将他的父类一起初始化)
类的加载整个分为三个部分
1. 加载
类加载器将字节码文件读入内存,并创建一个java.lang.Class对象
2. 连接
(1)验证
(2)准备
为类的静态Field分配内存,设置系统默认初始值
(3)解析
将常量池中的符号引用替换为直接引用
3. 初始化(主要是对staticField进行初始化)
1 2
1图的最后i值为3
2图的最后i值为2
根据顺序进行赋值,但1图中static代码块可以操作i变量,2图中不行,static代码块只对i进行赋值。