Java虚拟机那些事(2)

性能监控与故障处理工具

 JDK命令行工具

jps:虚拟机进程情况工具java

jstat:虚拟机统计信息监视工具bootstrap

jinfo:java配置信息工具安全

jmap:用于生成堆转储快照数据结构

jhat:虚拟机堆转储快照分析工具app

jstack:java堆栈跟踪工具工具

JDK可视化工具

jconsole性能

visualVMspa

类文件结构

1.魔数:这头四个字节惟一的做用是肯定这个文件是否为一个能被虚拟机接受的文件。命令行

2.次版本号和主版本号对象

3.常量池入口和容量计数器。常量池主要存放两大类常量:字面量和符号引用。

字面量:文本字符串,被声明为final的常量值。

符号引用(编译原理方面的概念):类和接口的全限定名,字段的名称和描述符,方法的名称和描述符。

4.访问标记:用于识别一些类或接口层次的访问信息

5.类索引、父类索引与接口索引集合:肯定这个类的继承关系

6.字段表集合

7.方法表集合

8.属性表集合

虚拟机类加载机制

虚拟机把描述类的数据从Class文件加载到内存,并对数据进行校验、转换解析和初始化,最终造成能够被虚拟机直接使用的java类型。

与那些在编译时须要进行链接工做的语言(如C++)不一样,java语言中,类型的加载和链接过程是在程序运行时完成的,这会增长一些性能开销,可是带来了更高的灵活性。

类加载的过程

1.加载:经过类的全限定名来获取定义此类的二进制字节流,将这个字节流所表明的静态存储转换为方法区的运行时数据结构,在java堆中生成了一个表明这个类的java.lang.Class对象,做为方法区这些数据的访问入口。

2.验证:确保Class文件的字节流中包含的信息符合当前虚拟机的要求,而且不会危害虚拟机自身的安全。文件格式验证,元数据验证(语义分析),字节码验证,符号引用验证。

3.准备:为类变量分配内存并设置类变量初始值,这些内存将在方法区进行分配。

4.解析:将常量池内的符号引用替换为直接引用的过程。类或接口的解析,字段解析,类方法解析,接口方法解析。

5.初始化:最后一步

类加载器

三种系统提供的类加载器:

1.启动类加载器(bootstrap classloader):加载JAVA_HOME/lib目录下的类库,没法被java程序使用。

2.扩展类加载器(extension classloader):加载JAVA_HOME/lib/ext目录下的类库。

3.应用程序类加载器(application classloader):也称为系统类加载器,它负载加载用户路径上所指定的类库。它是程序中默认的类加载器。

固然也能够自定义类加载器

双亲委派模型:若是一个类加载器收到了类加载的请求,它首先不会本身去尝试加载这个类,而是把这个请求委派给父类加载器去完成,每一个层次的类加载器都是如此。所以全部的加载请求最终会传达到顶层的启动类加载器中,只有加载器反馈本身没法完成这个加载请求时(找不到所需的类),子加载器才会尝试去加载。

缘由:避免混乱。由于就算是同一个类,不一样加载器加载的话,也会被认为是两个不一样的类。

 关于方法区的一些补充

 其实,从Java7开始就对方法区进行了一些调整;到Java8, 方法区的概念已经没有了,取而代之的是元空间MetaSpace这个概念。

Java7

符号引用:被挪到了本地内存

常量池和类的静态变量:被挪到了java堆

 Java8

类信息被挪到了本地内存区域,至次,方法区移除工做完成。

能够经过-XX:MetaspaceSize和-XX:MaxMetaspaceSize来进行调整元空间的大小。当超过大小设置时,会对死亡的类加载器和类进行GC 。

每一个类加载器存储区称为一个metaspace,会回收整个类加载器,减小碎片。

相关文章
相关标签/搜索