Java號稱“一次編譯到處運行”,你知道它的執行過程嗎?今天我來給大家分享一下
整篇乾貨我們通過具體的Demo來深入理解:
1、首先我們來寫一個java源文件
2、編譯。用javac或者ide工具將該java源文件編譯成java字節碼文件。
下面,再上一張java字節碼的總覽圖,剩下的我們按照順序一步一步解讀。
Java學習交流群632119504,歡迎喜歡Java的各位大神小神前來學習交流,每天晚上群裡面也會有大佬直播企業項目開發學習,更有各種項目案例供你自己學習哦
1、魔數,就是區分文件類型的一種標誌。對應我們Demo的就是0XCAFE BABE。
2、版本號,版本號分主版本號和次版本號,都是各佔2個字節。在此Demo種為0X0000 0033。前面的是次,後面的是主。通過進制轉換得到的是次版本號為0,主版本號為51。
3、常量池,常量池是Class文件中的資源倉庫,主要是字面量和符號引用。
下面來一張常量池的項目類型表,JDK1.7之後可能還有新加的,還是按照Demo的字節碼進行逐一翻譯。
4、Access_Flag 訪問標誌,訪問標誌信息包括該Class文件是類還是接口,是否被定義成public,是否是abstract,如果是類,是否被聲明成final。通過上面的源代碼,我們知道該文件是類並且是public。
注意:0x 00 21:是0x0020和0x0001的並集。其中0x0020這個標誌值涉及到了字節碼指令,這裡暫不多說
5、類索引,類索引用於確定類的全限定名
0x00 03 表示引用第3個常量,同時第3個常量引用第19個常量,查找得"com/demo/Demo"。#3.#19
6、父類索引
0x00 04 同理:#4.#20(java/lang/Object)
7、接口索引
通過java_byte.jpeg圖我們知道,這個接口有2+n個字節,前兩個字節表示的是接口數量,後面跟著就是接口的表。我們這個類沒有任何接口,所以應該是0000。果不其然,查找字節碼文件得到的就是0000。
8、字段表集合,字段表用於描述類和接口中聲明的變量。這裡的字段包含了類級別變量以及實例變量,但是不包括方法內部聲明的局部變量。
下面上一張字段表結構圖
果不其然:
0x00 02 :訪問標誌為private(自行搜索字段訪問標誌)
0x00 05 : 字段名稱索引為#5,對應的是"a"
0x 00 06 :描述符索引為#6,對應的是"I"
0x 00 00 :屬性表數量為0,因此沒有屬性表。
tips:一些不太重要的表(字段,方法訪問標誌表)可以自行搜索,這裡就不貼出來了,防止篇幅過大。
9、方法,方法解析,按照下圖解析(Java學習群632119504)
10、方法解析完成,解析Attributes一下就可以了
其實,我們寫了這麼多確實很麻煩,不過這種過程自己體驗一遍的所獲所得還是不同的。這樣以後我們也能看懂字節碼文件了。瞭解class文件的結構對後面進一步瞭解虛擬機執行引擎非常重要,所以這是基礎並重要的一步。(Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、Java、)
最後來看一下使用java自帶的反編譯器來解析字節碼文件是什麼樣子的吧