不管是现在安卓使用的kotlin还是groovy,Scala这些,其实都是运行在Java虚拟机之上的,类似这样的特性被称为语言无关性,而这个特性就是今天主要要说的。

语言无关性的基础

实现语言无关性的基础是虚拟机和字节码存储格式Java虚拟机只是与class文件这种特定的二进制文件有着关联

对于Java语言来说,其中的语法、关键字之类的最终都会变成多条字节码指令组合来表示,这里也从侧面说明了字节码指令的语言描述能力比Java语言本身更强。这样就使得虚拟机不局限于一种语言。

程序经过编译的环节变为不受语言限制的二进制.class字节码文件,再经由虚拟机变为机器指令。

Class类文件结构

Class文件由两种数据结构组成,无符号数表。

无符号数即基本的数据类型,数字、引用、常量这些都可以用它来表示。

表是多个无符号数或者多张表构成的比较复杂的数据结构。

文件结构的身份识别:

对于class文件来说,每个文件的头四个字节为魔数

魔数的唯一作用是表明它是不是一个能被虚拟机接受的class文件,即用作身份识别。事实上除开class文件,其他的很多文件格式,比如JPEG等都用魔数来进行身份识别。

这里与我们通常理解不一样的是,我们会误认为文件使用扩展名来进行识别,然而事实上扩展名非常容易被修改,从这一点上来说它是不安全的,因此不会采用这种方式。

常量池:

看每个java进程占用内存 java进程查看_看每个java进程占用内存

如图,class文件中依次存放魔数、class文件的主次版本号之后,接着放的就是常量池的入口。

常量池中放的一般是两种,一种叫字面量,其实就可以看作普通的常量。第二种叫符号引用,这里的常量主要包括字段、方法的描述,方法的句柄,动态常量等。(注:这里面的常量是上文中提到的表,表共有十七中不同的类型)

访问标志、类索引、父索引、借口索引:

看每个java进程占用内存 java进程查看_Java_02

如图,在常量池之后的是访问标志,主要用来识别一些类或者借口的访问信息,比如这个类是具体的还是一个接口,是否是抽象的(abstract)这样

类索引的作用是确定这个类的全限定名

类的全限自定义域名 定名:

全限定名有绝对路径的意思

Java类包的定名:com.linux.struct.sort.bubblesort,从最原始最上层的地方援引到具体的对象,这就是全限定名了。

一个文件file的存放路径,其绝对路径可能是/usr/local/sbin/file;

本段转载于

父类索引是为了确定这个类父类的全限定名。

接口索引是记录它这个类实现了哪些接口。

字段表:

字段表用于描述接口或者类中声明的变量。Java中的字段包括类的变量以及实例的变量,但是不包括局部变量。

方法表:

其结构与功能与字段表类似,不过它这里面放的是对方法的描述。

属性表:

这里面放的是不管class文件也好,前面的方法表字段表也好的自己的属性。这部分比较复杂,之后单独写一篇博客。

进程查看小工具(jdk自带)

1、JPS:可以用来查看当前正在运行的进程以及名称

看每个java进程占用内存 java进程查看_Java_03

这里是先进入了我的jdk的bin目录,然后调用该工具的示意图

2、JSTAT:查看当前某一个进程所占用Java堆的情况

看每个java进程占用内存 java进程查看_看每个java进程占用内存_04

里面涉及到了各个区域内存的占用情况以及GC的花费时间。