初识class文件
2021-10-22 本文已影响0人
Raral
public class TestCal {
public int cal() {
int i = 10;
int j = 5;
int res = i / j;
return res;
}
public int sum() {
int a = 10;
int b = 5;
int res2 = a + b;
return res2;
}
public static void main(String[] args) {
TestCal testCal = new TestCal();
testCal.cal();
testCal.sum();
}
}
Last modified 2021-10-21; size 454 bytes
MD5 checksum 5622b537b271592ce3a87419b9ae06e0
Compiled from "TestCal.java"
public class TestCal // 魔法数字,表明当前文件是.class文件,固定0xCAFEBABE
minor version: 0 //分别为Class文件的副版本和主版本
major version: 52
flags: ACC_PUBLIC, ACC_SUPER //类访问标识
Constant pool: // 线程共享内存 -> 方法区 -> 运行时常量池区
#1 = Methodref #6.#18 // java/lang/Object."<init>":()V
#2 = Class #19 // TestCal
#3 = Methodref #2.#18 // TestCal."<init>":()V
#4 = Methodref #2.#20 // TestCal.cal:()I
#5 = Methodref #2.#21 // TestCal.sum:()I
#6 = Class #22 // java/lang/Object
#7 = Utf8 <init>
#8 = Utf8 ()V
#9 = Utf8 Code
#10 = Utf8 LineNumberTable
#11 = Utf8 cal
#12 = Utf8 ()I
#13 = Utf8 sum
#14 = Utf8 main
#15 = Utf8 ([Ljava/lang/String;)V
#16 = Utf8 SourceFile
#17 = Utf8 TestCal.java
#18 = NameAndType #7:#8 // "<init>":()V
#19 = Utf8 TestCal
#20 = NameAndType #11:#12 // cal:()I
#21 = NameAndType #13:#12 // sum:()I
#22 = Utf8 java/lang/Object
{
public TestCal();
descriptor: ()V //当前方法是 返回viod
flags: ACC_PUBLIC //当前方法是 访问修饰符 public
Code: //字节码指令
stack=1, locals=1, args_size=1 // 本地局部变量:[ this ]
0: aload_0 // 将第1个引用类型本地变量推送至栈顶(this)
1: invokespecial #1 // Method java/lang/Object."<init>":()V // 调用超类构建方法, 实例初始化方法, 私有方法(这些方法在编译器就可确定)
4: return //当前方法返回void
LineNumberTable: //java的源码的行号和字节码指令对应关系
line 1: 0
public int cal();
descriptor: ()I //当前方法是 返回int
flags: ACC_PUBLIC //当前方法是 访问修饰符 public
Code: //字节码指令
stack=2, locals=4, args_size=1 // 本地局部变量:[ this, i, j, res ]
0: bipush 10 //将单子节的常量值(10)推送至栈顶;操作数栈:[ 10 ] 本地局部变量:[ this, i, j, res ]
2: istore_1 //将栈顶int类型的值存入第二个本地变量; 操作数栈:[ ] 本地局部变量:[ this, 10, j, res ]
3: iconst_5 //将常数int类型值5推送至栈顶; 操作数栈:[ 5 ] 本地局部变量:[ this, 10, j, res ]
4: istore_2 //将栈顶int类型的值存入第三个本地变量; 操作数栈:[ ] 本地局部变量:[ this, 10, 5, res ]
5: iload_1 //将第二个int型本地变量(10)推送至栈顶; 操作数栈:[ 10 ] 本地局部变量:[ this, 10, 5, res ]
6: iload_2 //将第三个int型本地变量(5)推送至栈顶; 操作数栈:[ 5, 10 ] 本地局部变量:[ this, 10, 5, res ]
7: idiv //将栈顶两int型数值相除并将结果压入栈顶(10 / 5 ); 操作数栈:[ 2 ] 本地局部变量:[ this, 10, 5, res ]
8: istore_3 //将栈顶int类型的值存入第四个本地变量; 操作数栈:[ ] 本地局部变量:[ this, 10, 5, 2 ]
9: iload_3 //将第四个int型本地变量(2)推送至栈顶; 操作数栈:[ 2 ] 本地局部变量:[ this, 10, 5, 2 ]
10: ireturn //从当前方法返回int(2)
LineNumberTable:
line 4: 0
line 5: 3
line 6: 5
line 7: 9
public int sum();
descriptor: ()I
flags: ACC_PUBLIC
Code:
stack=2, locals=4, args_size=1
0: bipush 10
2: istore_1
3: iconst_5
4: istore_2
5: iload_1
6: iload_2
7: iadd
8: istore_3
9: iload_3
10: ireturn
LineNumberTable:
line 11: 0
line 12: 3
line 13: 5
line 14: 9
public static void main(java.lang.String[]);
descriptor: ([Ljava/lang/String;)V
flags: ACC_PUBLIC, ACC_STATIC
Code:
stack=2, locals=2, args_size=1 // 本地局部变量:[ this,testCal ] ;操作数栈:[ testCal引用地址(ox123456) ] 右边是顶部
0: new #2 // class TestCal `//创建一个对象, 并将其引用引用值压入栈顶;操作数栈:[ testCal引用地址(ox123456) ] 本地局部变量:[ this,testCal ]
3: dup // 复制栈顶数值并将复制值压入栈顶; [ testCal引用地址copy(ox123456), testCal引用地址(ox123456) ] 本地局部变量:[ this,testCal ]
4: invokespecial #3 // Method "<init>":()V //// 调用超类构建方法, 实例初始化方法, 私有方法(这些方法在编译器就可确定);[ testCal引用地址copy(ox123456), testCal引用地址(ox123456) ] 本地局部变量:[ this,testCal ]
7: astore_1 //[ testCal引用地址copy(ox123456) ] 本地局部变量:[ this,testCal引用地址(ox123456) ]
8: aload_1 // //[testCal引用地址(ox123456), testCal引用地址copy(ox123456) ] 本地局部变量:[ this,testCal引用地址(ox123456) ]
9: invokevirtual #4 // Method cal:()I //调用实例方法 testCal引用地址copy(ox123456)调用
12: pop //将栈顶数值弹出(数值不能是long或double类型的);[testCal引用地址(ox123456) ] 本地局部变量:[ this,testCal引用地址(ox123456) ]
13: aload_1 ///[testCal引用地址(ox123456), testCal引用地址copy(ox123456) ] 本地局部变量:[ this,testCal引用地址(ox123456) ]
14: invokevirtual #5 // Method sum:()I //调用实例方法 testCal引用地址copy(ox123456)调用
17: pop ////将栈顶数值弹出(数值不能是long或double类型的)
18: return //当前方法无返回
LineNumberTable:
line 19: 0
line 20: 8
line 21: 13
line 22: 18
}
SourceFile: "TestCal.java"
// bipush(push): 表示 从不知道哪里的数据 推送至栈顶
// istore_1(store): 表示 从 栈顶的数据 存入本地变量对应的下标位置
// iconst_5(const): 表示 从 常数的数据 推送至栈顶
// iload_1(load): 表示 从本地局部变量 推送至栈顶
// idiv(div): 表示 栈顶相邻的数据 做 除法操作 后;推送至栈顶
//ireturn : 返回 int