JVM和类的关系
当我们调用JAVA命令运行某个java程序时,该命令将会启动一条java虚拟机进程,不管该java程序有多么复杂,该程序启动了多少个线程,它们都处于该java虚拟机进程里.正如前面介绍的,同一个JVM的所有线程、所有变量都处于同一个进程里,它们都使用该JVM进程的内存区。
当系统出现以下几种情况时,JVM进程将被终止:
l 程序运行到最后正常结束。
l 程序运行到使用System.exit()或Runtime.getRuntime().exit()代码结束程序
l 程序执行过程中遇到未捕获的异常或错误而结束
l 程序所在平台强制结束了JVM进程
类的加载
当程序主动使用某个类时,如果该类还未被加载到内存中,系统会通过加载、连接、初始化步骤来对该类进行初始化,如果没有意外,JVM将会连续完成这三个步骤,所以有时也把这三个步骤统称为类加载或类初始化。
类加载指的是将类的Class文件读入内存,并为之创建一个java.lang.Class对象,也就是说当程序中使用任何类时,系统都会为之建立一个java.lang.Class对象。
类的加载由类加载器完成,类加载器通常由JVM提供,这些类加载器也是我们所有程序运行的基础,JVM提供的这些类加载器通常被称为系统类加载器。除此之外,开发者可以通过继承ClassLoader基类来创建自己的类加载器。
类加载器加载的文件:
l 从本地系统中加载class文件
l 从JAR包中加载class文件
l 通过网络加载class文件
l 把一个java源文件动态编译、并执行加载
类的连接
类连接分为3个阶段:
验证:检验被加载的类是否有正确的内部结构,并和其他类协调一致
准备:为静态属性分配内存,并设置默认初始值
解析:将类中的二进制数据中的符号引用替换成直接引用(final修改的常量的替换)
类的初始化
主要是对静态属性进行初始化
JVM初始化一个类包含以下几个步骤:
l 假如这个类还没有被加载和连接,程序先加载并连接该类
l 假如该类的直接父类还没有被初始化,则先初始化其直接父类
l 假如类中有初始化语句,则系统依次执行这些初始化语句。
什么时候会导致类加载或者类初始化?
l 创建类的实例(new方法)
l 调用某个类的静态方法
l 访问某个类或者接口的静态属性
l 使用反射机制来强制创建某个类或接口对应的java.lang.Class对象。(Class.forName(“Person”))
l 初始化某个类的子类
l 直接使用java.exe命令来运行某个主类
备注:
当使用ClassLoader类的loadClass方法来加载某个类时,该方法只是加载该类,并不会执行该类的初始化。当使用Class的forName()静态方法才会导致强制初始化该类。