类文件结构public class TestClass {private int m;public int inc() {return m + 1; }}1.魔数 每个Class文件的头四个字节被称为 TestClass.java"4.访问标志 在常量池之后就是2个字节代表访问标志 access_flags。 ,ACC_SYNTHETIC,ACC_ANNOTATION,ACC_ENUM,ACC_MODULE0x0021其中2表示ACC_SUPER,1表示ACC_PUBLIC5.类索引,父类索引,接口索引集合 又印证了java会给每一个类隐式定义一个构造方法。 而我的方法明明没有参数,为什么又有Arg_size=1呢? Java语言的潜规则:在任实例方法中,都可以通过this访问到方法所属的对象——哈哈哈哈,我猜大家平时在写代码的时候在方法内引用当前类的属性都不会显式的把this.给写出来,而是直接拿属性了。
Class文件是以8位字节为基础单位的二进制流,各部分中间没有分隔符。遇到8位字节以上的空间数据项时,则会按照高位在前的方式分割成若干个8位字节进行存储。 Class文件采用类似C语言的伪结构体来存储,这种伪结构体只有两种数据类型:无符号数和表。无符号数以u1,u2,u4,u8四种,数字代表字节数。 表用于描述有层次关系的复合结构数据,整个Class文件本质上就是一张表。 2.接口的访问信息 类索引、父类索引 和接口索引集合 存储类、父类、接口的 文件索引 字段表集合 1.字段作用域 2.是否static 3.可变性 4.并发可见性 5.可否被序列化 6.字段数据类型 7 因为Java不支持多重继承,所以父类索引只有一个,除了java.lang.Object外,所有Java类都有父类,因此除了java.lang.Object,所有java类的父类索引都不为0。
前言 在上一篇文章中我们一起来看了一下 Java 虚拟机的类加载过程,包括虚拟机加载、验证、准备、解析和初始化 5 个大步骤,同时我们还讨论了 Java 虚拟机加载类时采用的双亲委派模型思想。 解析 .class 文件 我们都知道一个 Java 类(.java)文件在被 Java 编译器(javac) 编译过后,如果语法没有错误,则会生成一个对应的 .class 文件,这个 .class 文件是一个二进制文件,用一定的格式保存了我们书写的类的所有信息。 除了 ConstantValue 以外,Java 虚拟机还有很多其他类型的属性表,最常见的便是 Code 表,它的结构我们在分析类文件中的方法属性时会介绍,如果虚拟机在进行属性表解析时发现属性表名不是其可以识别 其实 验证过程是最复杂的,因为这个过程需要扫描整个在加载过程中得到得到的 .class 文件格式的二进制数据,也就是相当于将我们在上面模拟的解析 .class 文件的过程,并且判断相关的数据是否合法,比如文件的魔数是否为
: Bad version number in .class file 就是由于JDK1.6编译的文件版本号超过了JDK1.5虚拟机所接受的范围 Java class文件是二进制文件。 #3 // String Hello,World 5: invokevirtual #4 // Method java/ Class类文件结构 class文件的结构 简单讲,jvm的class文件是针对jvm的私家定制。只要运行在jvm上byte code,都需要按照class文件format来。否则jvm解析不了。 官网文档: The Java Virtual Machine class file format class文件时java虚拟机执行引擎的数据入口,也是java技术体系的基础支柱之一,了解class文件的结构对后面进一步了解虚拟机执行引擎有很重要的意义 class文件是一组以八位字节为基础单位的二进制流,各个数据项目严格按照顺序紧凑地排列在class文件中,中间没有添加任何分隔符,这使得整个class文件中存储的内容几乎全部都是程序运行的必要数据,没有空隙存在
.*; import java.io.*; import java.text.ParseException; import java.text.SimpleDateFormat; import java.util .*; /** * 使用Java的mail包解析 标准的 .eml格式的邮件文件 * * @author * @date 2019/08/07 */ public class EmlUtil HashMap<>(); parserFile(file.getAbsolutePath()); return result; } /** * 解析文件 * * @param emlPath 文件路径 */ public Map<Object, Object> parserFile(String emlPath) map.put("type", msg.getContentType()); } return map; } /** * 解析内容
java的运行过程 在运行一段java代码的时候需要经过编译,验证,加载和运行,具体如下图: ? 这个系列的文章是为了探讨Java字节码是什么样的结构,如何能够准确的表达我们代码的含义。 ---- JDK中如何解析class文件 在原生的JDK中有对java字节码的读取的工具类com.sun.tools,具体使用如下: File file=new File("/Users/fuwei/work class文件的基本结构 根据JVM的虚拟机规范(SE8)提供的资料,字节码对应的结构体如下: ClassFile { u4 magic; u2 在我们了解了class的结构之后,就可以开始试着解析class文件。 解析过程 读取类文件 private DataInputStream dataInputStream; public ClassReadCursor(String filePath) {
本文将为你介绍如果使用Java的Scanner类来读取或者解析CSV文件。 我的CSV文件(user.csv)内容如下 Rockey,22,India Bill,23,US Sonia,23,Germany 接下来我们首先从创建映射上述属性的实体User.java public ,本例中我们采用文件的方式。 CSVParsingExample.java import java.io.File; import java.io.IOException; import java.util.ArrayList; import java.util.List; import java.util.Scanner; public class CSVParsingExample { public static void
Java虚拟机不和包括Java在内任何语言绑定,它只与Class文件这种特定的二进制文件格式所关联,Class文件中包含了Java虚拟机指令集和符号表以及若干其他辅助信息。 二.Class文件结构 根据Java虚拟机规范,类文件由单个ClassFile结构组成: ClassFile{ u4 magic; //Class 文件的标志 u2 [attributes_count];//属性表集合 } 根据Java虚拟机规范规定,Class文件格式采用一种类似C语言结构体的伪结构来存储数据,这种伪结构中只有两种数据类型:无符号和表 无符号数属于基本的数据类型 第5和第6个字节是次版本号,第7和第8字节是主版本号(0x0034为52,对应JDK版本1.8)Java的版本号是从45开始的,JDK1.1之后的每一个JDK大版本发布主版本号向上加1,高版本的JDK能向下兼容低版本的 当虚拟机运行时,需要从常量池获得对应的符号引用,再在类创建或运行时解析并翻译到具体的内存地址中。
我们可以查看上述字节码的二进制文件用16进制查看: ? 如果一个 class 文件的魔术不是 0xCAFEBABE,那么虚拟机将拒绝运行这个文件 次版本号(minor version):.class 文件的第 5 - 6 个字节,即编译生成该 .class 字节码的二进制文件对应表示为: CA FE BA BE 00 00 00 34 那么前面的cafebabe就是魔数,而0000 和0034则分别是主版本号和次版本号。 、父类索引和接口索引集合 在class文件中,将用这三项来标识类的继承关系。 这个类属性值表示的内容为: SourceFile: "HelloByteCode.java" 至此,我们完整解析了class类的字节码。
目录 Java中的包概念 - [包的作用](#%E5%8C%85%E7%9A%84%E4%BD%9C%E7%94%A8) - [package 的目录结构](#package-%E7% 包名必须与相应的字节码所在的目录结构相吻合。 下面是管理你自己 java 中文件的一种简单方式: 将类、接口等类型的源码放在一个文本中,这个文件的名字就是这个类型的名字,并以.java作为扩展名。 3) java.util:包含实现像链接列表,字典和支持等数据结构的实用类; 用于日期/时间操作。 4) java.applet:包含用于创建Applets的类。 .class文件本质上是一种二进制文件, 它一般是由.java文件通过 javac这个命令(jdk本身提供的工具)生成的一个文件, 而这个文件可以由jvm(java虚拟机)装载(类装载),然后进java class文件是字节码文件,由.java源文件通过javac命令编译后生成的文件。是可以运行在任何支持Java虚拟机的硬件平台和操作系统上的二进制文件。.class文件并不本地的可执行程序。
“ 我们都知道Java虚拟机不和包括Java在的任何语言绑定,它只与Class文件这种特定的二进制文件格式所关联。而Class文件是由java文件经过javac编译器编译后生成的。” ? 01 — Class类文件结构 在深入理解Java虚拟机一书中是先介绍概念然后具体分析,这里我就反过来描述,我们先看一下class文件,这里我打开一个本地被编译过的class文件,我们看到它是乱码的。 当虚拟机运行时,需要从常量池获得对应的符号引用,再在类创建时或运行时解析并翻译到具体的内存地址之中。 Class文件是一组以8字节为基础单位的二进制流,各个数据项目严格按照顺序紧凑排列在class文件中,中间没有任何分隔符,这使得class文件中存储的内容几乎全部是程序运行的必要程序。 Java虚拟机规范规定,Class文件格式采用类似C语言结构体的伪结构来存储数据,这种结构只有两种数据类型:无符号数和表
而 class 文件便是一组以 8 位字节为基础单位流的二进制流,各个数据项目严格按照顺序紧凑地排列在 class 文件之中,中间没有添加任何分隔符,所以整个class 文件中存储的内容几乎都是程序运行的必要数据 4、魔数 每个 class 文件的头 4 个字节称为魔数(Magic Number),它的唯一作用是:标识该文件是一个Java类文件。 如果没有识别到该标志,则说明该文件不是Java类文件或者文件已受损。 由上图,我们可以看到前 4 个字节是 cafe babe。 5、Class 文件的版本号 紧随魔数的 4 个字节存储的是 class 文件的版本号:第 5 和第 6 个字节是次版本号(Minor Version),第 7 和第 8 个字节是主版本号(Major 当虚拟机运行时,需要从常量池获得对应的符号引用,再在类创建时或运行时解析并翻译到具体的内存地址之中。关于类的创建和动态连接的内容,下篇博客会详细介绍。
Java虚拟机不和特定的语言绑定,它只与 “Class文件” 这种特定的二进制文件格式所关联。Class文件中包含了 Java虚拟机指令集和符号表以及若干其他辅助信息。 Class 类文件的结构 ---- Class 文件是一组以8位字节为基础单位的二进制流,各个数据项目严格按照顺序紧凑地排列在 Class文件之中,中间没有任何分隔符,这使得整个 Class文件中存储的内容几乎全部是程序运行的必要数据 Java虚拟机规范中规定,Class文件格式采用一种类似于C语言结构体的伪结构来存储数据,这种伪结构中只有两种数据类型:无符号数和表,后面的解析都要以这两种数据类型为基础,所以这里先介绍这两个概念。 根据 Java 虚拟机规范,类文件由单个 ClassFile 结构组成: ClassFile { u4 magic; //Class 文件的标志 u2 Class文件的魔数值很有“浪漫气息”,值为 “0xCAFEBABE(咖啡宝贝)” 紧接着魔数的4个字节存储的是 Class文件的版本号:第5和第6个字节存储的是次版本号(Minor Version),
先从 HashMap 开始: HashMap HashMap 应该是 Java 集合框架中我们在开发中最常用的容器类之一了,它提供了保存多个键值对的能力,并对其保存的键值对提供获取和操作的相关 API, 而所有位运算均是争对二进制而言,这个方法的作用是什么呢? 我们用一个具体的数值带进去走一遍流程,假设当前 cap 为 6: n = cap - 1 = 5 n 的二进制:000..00(29个0) 101,之后省略前导零 n |= n >>> 1 = (101 没错,这个具体类就是依赖于红黑树构建的,可能有小伙伴会说了,怎么又是红黑树啊,其实红黑树是一种很有用的数据结构,只是维护的时候比一般的二叉搜索树复杂一点(主要是为了维护高度平衡以保证较高的查找效率),关于代码中怎么去维护它的高度我们就不去深追究了 好了,思路就到这里了,下面来看看代码: import java.util.Map; import java.util.TreeMap; public class CustomTreeMapSortMethod
本文,我们编写JAVA程序来解析class文件,读者注意,阅读本文前先详细了解Class文件结构,可参考笔者前一篇文章:Class文件结构(1)—手动解析每一个字节,你看不懂 代码地址:https 在实现常量池解析器之前,我们需要先根据《Java虚拟机规范》中描述的每个常量结构创建对应的Java类型。 在创建完各常量结构对应的Java类,和实现各常量结构的解析方法后,我们再来完成整个常量池的解析工作。 方法包括静态方法、以及类的初始化方法<clinit>和类的实例初始化方法<init>。参照《Java虚拟机规范》,方法结构如表 ? 了解Class文件结构是学习Java虚拟机字节码指令的前提条件。 下一篇我们正式学习字节码指令!
通过 Dockerfile 开发人员可以快速创建自定义镜像,这篇文章就为大家来介绍一下 Dockerfile的文件结构 Dockerfile 内容包含四部分: 基础镜像信息 维护者信息 镜像操作指令 容器启动时执行的指令 下面我们通过一个 Dockerfile 文件来具体讲解一下: # 这个 Dockerfile 是基于 ubuntu:xeniel 镜像来创建容器 FROM ubuntu:xeniel nginx RUN echo "\ndaemi off;">>/etc/nginx/nginx.conf CMD /usr/sbin/nginx 第一行通过注释的方式描述了这个 Dockerfile 文件是基于
如果你也和我一样,不了解类结构和类加载,但是工作中又涉及到字节码相关内容,相信后面两篇文章会对你有所帮助。 我们所编写的每一行代码,要在机器上运行最终都需要编译成二进制的机器码 CPU 才能识别。 它们和 Java 语言一样都会被编译器编译成字节码文件,然后由虚拟机来执行。所以说类文件(字节码文件)具有语言无关性。 二. Class 文件结构 Class 文件是一组以 8 位字节为基础单位的二进制流,各个数据严格按照顺序紧凑的排列在 Class 文件中,中间无任何分隔符,这使得整个 Class 文件中存储的内容几乎全部都是程序运行的必要数据 Java 虚拟机规范规定 Class 文件格式采用一种类似与 C 语言结构体的微结构体来存储数据,这种伪结构体中只有两种数据类型:无符号数和表。 建议想要深入了解的同学可以自己动手将 Java 类编译成二进制字节码文件,根据文章里介绍的类文件结构逐个字符去对照和实验,有助于加深理解。
如果你也和我一样,不了解类结构和类加载,但是工作中又涉及到字节码相关内容,相信后面两篇文章会对你有所帮助。 我们所编写的每一行代码,要在机器上运行最终都需要编译成二进制的机器码 CPU 才能识别。 Class 文件结构 Class 文件是一组以 8 位字节为基础单位的二进制流,各个数据严格按照顺序紧凑的排列在 Class 文件中,中间无任何分隔符,这使得整个 Class 文件中存储的内容几乎全部都是程序运行的必要数据 Java 虚拟机规范规定 Class 文件格式采用一种类似与 C 语言结构体的微结构体来存储数据,这种伪结构体中只有两种数据类型:无符号数和表。 建议想要深入了解的同学可以自己动手将 Java 类编译成二进制字节码文件,根据文章里介绍的类文件结构逐个字符去对照和实验,有助于加深理解。 关于「类文件结构」我们就介绍到这里,下一篇我们来聊聊「虚拟机的类加载机制」。 参考资料: 《深入理解 Java 虚拟机:JVM 高级特性与最佳实践(第 2 版)》 ----
Java虚拟机不和包括Java在内的任何语言绑定,它只与“Class文件”这种特定的二进制文件格式所关联,Class文件中包含了Java虚拟机指令集和符号表以及若干其他辅助信息。 任一门功能性语言都可以表示为一个能被Java虚拟机所接受的有效的Class文件,所以虚拟机并不关系Class的来源是何种语言2.Class类文件的结构任何一个Class文件都对应着唯一一个类或接口的定义信息 Class文件说一组以8位字节为基础单位的二进制流,各个数据项目严格的按照顺序紧凑地排列在Class文件中,中间没有任何分隔符,所以Class文件中存储的内容几乎都是程序运行的必要数据,没有空隙存在当遇到需要占用 8位字节以上空间的数据项时,则会按照高位在前的放松分割成若干个8位字节进行存储Class文件格式采用一种类似于V语言结构体的伪结构体存储数据,伪结构中只有两周数据类型:无符号数、表无符号数属于基本数据类型 当虚拟机运行时,,需要从常量池获得对应的符号引用,再在类创建时或运行时解析、翻译到具体的内存地址之中。
类文件结构JVM 的“无关性” 谈论 JVM 的无关性,主要有以下两个:平台无关性:任何操作系统都能运行 Java 代码语言无关性: JVM 能运行除 Java 以外的其他代码Java 源代码首先需要使用 Class 文件结构 Class 文件是二进制文件,它的内容具有严格的规范,文件中没有任何空格,全都是连续的 0/1。Class 文件 中的所有内容被分为两种类型:无符号数、表。 版本信息紧接着魔数的 4 个字节是版本信息,5-6 字节表示次版本号,7-8 字节表示主版本号,它们表示当前 Class 文件中使用的是哪个版本的 JDK。 CONSTANT_utf8_info1UTF-8 编码的字符串CONSTANT_Integer_info3整型字面量CONSTANT_Float_info4浮点型字面量CONSTANT_Long_info5长整型字面量 由于 Java 不允许多重继承,所以父类索引只有一个,除了 java.lang.Object 之外,所有的 Java 类都有父类,因此除了 java.lang.Object 外,所有 Java 类的父类索引都不为