目录
java 是解释执行的还是编译执行的
其实是混合的。
对常用的代码会即时编译到本地。下次运行的时候就不需要通过解释器一句一句,执行引擎可以直接调用操作系统。
不是所有代码都会jit即时编译的。
java是个跨语言平台, 是因为jvm的原因。
jvm上跑的语言特别多,应该是100多种。
jvm虚拟机本身就是个规范,虚构出来的一台计算机
- 字节码指令集(汇编语言)
- 内存管理:栈 堆 方法区等
任何语言都会编译成class 如果不是编译也是会生成二进制class 然后再jvm执行
jvm和java无关。
既然是规范 也就类似于接口 那么就会有各种各样的实现。
JVM实现
HotSpot
- oracle官方,我们做实验用的jvm
- java -version
Jrockit
- BEA,曾经号称世界上最快jvm BEA是创始人三个人的首字母
- 被oracle收购,合并于HotSpot
J9 -IBM
Microsoft VM
TaobaoVM
- hostspot深度定制版
LiquidVM
- 直接针对硬件
zuil zing 土豪才用的起的商业版本 特点就是快 特别是垃圾回收 1毫秒以内 ZGC就是参考这个回收
- 最新垃圾回收的业界标杆
- www.zul.com
一流企业做标准
二流企业定服务
三流企业做产品
查看JVM类型
如果搭配好了本地环境 可以输入命令
java -version
就可以看到
可以看到是HotSpot,也是最常见的一个。
JDK JRE JVM 到底是什么关系?
jvm 只是来执行的。里面包括一系列关于class的存储 运行 方法区 等等。 总的来说 是执行的核心地。
jre 除了虚拟机之外 还要有核心类库 要比jvm更大的
jdk 开发用的包 这些工具 包含 jre jvm
class文件
Class File Format
就是编译过后的class
二进制流
数据类型 u1 u2 u4 u8 和 _info(表类型)
info的来源是hotspot源码中的写法
查看16进制格式的ClassFile
sublime/notepad/
idea插件-BinEd
有很多可以观察ByteCode的方法:
javap
JBE - 可以直接修改
JClassLib -IDEA插件之一
class构成
CAFE BABE 这就是java编译的文件 也叫做magic number exe文件里也有类似的东西
除了CAFE BABE 过后 jdk1.8就是 00000034 前4位minor version 后四位major version 34进制转换成10进制也就是52
所以这也是看lib的jar包会显示52。其实就是jdk1.8的意思。
constant_pool_conut 常量池的编号是从1 开始 一般数组是从0开始 将来没准表示不指向任何常量 就可以指向0 就有那么一种可能性
常量表所以就是16-1 15
这就是插件BinEd可以直接查看16进制的class文件,具体的可以百度搜索方法。
但是这样其实也是看不太懂的 不知道具体的意义。那么可以再弄另一个插件 也是我比较推荐的一个插件JClassLib。帮助我们分析class里面有什么内容
他会把class 文件进行一系列的分析 分段 其实对应的就是class文件的16进制 更方便阅。(最新版的已经改了中文)
Minor version 小版本
Major version 大版本 已经给你翻译成jdk1.8
constantpoolcount 常量池的最大单位
Accessflags 描述当前类的访问修饰符
ACC_PUBLIC 0x0001 public类型 所有类型
ACC_FINAL 0x0010 final类型 类
ACC_SUPER 0x0020 使用新的invokespecial语义 类和接口
ACC_INTERFACE 0x0200 接口类型 接口
ACC_ABSTRACT 0x0400 抽象类型 类和接口
ACC_SYNTHETIC 0x1000 该类不由用户代码生成 所有类型
ACC_ANNOTATION 0x2000 注解类型 注解 jdk1.5以后出的
ACC_ENUM 0x4000 枚举类型 枚举 jdk1.5以后出的
它是可以组合的 所以0x0021 代表的就是 public 和super 也就是第一个和第三个 ,super是每个类都有的不用去管它
This class:这个类的名称 cp_info # 2 代表放在常量池的二号位 后面是它的名称
Super class : 父类的名称 放在常量池的三号位
interfaces count:实现的接口数量
FiledCount:里面的属性数量
Methods count:方法数量 默认会有一个空参构造
Attributes count 附加字段数量