一、加载与存储指令
1.1、加载常量到操作数栈
类别 | 指令 | 作用 | 常量范围 / 说明 | Java 代码示例 | 字节码示例 |
---|---|---|---|---|---|
int 常量 | iconst_m1 |
加载 int 常量 -1 |
仅 -1 |
int a = -1; |
iconst_m1 istore_1 |
iconst_0 |
加载 int 常量 0 |
仅 0 |
int b = 0; |
iconst_0 istore_2 |
|
iconst_5 |
加载 int 常量 5 |
仅 5 |
int c = 5; |
iconst_5 istore_3 |
|
bipush |
加载 8 位有符号 int 常量 | -128 ~127 |
int d = 100; |
bipush 100 istore_4 |
|
sipush |
加载 16 位有符号 int 常量 | -32768 ~32767 |
int e = 2000; |
sipush 2000 istore_5 |
|
ldc |
从常量池加载 int | 超出sipush 范围的 int |
int f = 40000; |
ldc #2 istore_6 |
|
long 常量 | lconst_0 |
加载 long 常量 0L |
仅 0L |
long g = 0L; |
lconst_0 lstore_7 |
lconst_1 |
加载 long 常量 1L |
仅 1L |
long h = 1L; |
lconst_1 lstore_9 |
|
ldc2_w |
从常量池加载 long | 超出lconst 范围的 long |
long i = 1000L; |
ldc2_w #3 lstore_11 |
|
float 常量 | fconst_0 |
加载 float 常量 0.0f |
仅 0.0f |
float j = 0.0f; |
fconst_0 fstore_13 |
fconst_2 |
加载 float 常量 2.0f |
仅 2.0f |
float k = 2.0f; |
fconst_2 fstore_14 |
|
ldc |
从常量池加载 float | 超出fconst 范围的 float |
float l = 3.14f; |
ldc #4 fstore_15 |
|
double 常量 | dconst_0 |
加载 double 常量 0.0 |
仅 0.0 |
double m = 0.0; |
dconst_0 dstore_16 |
dconst_1 |
加载 double 常量 1.0 |
仅 1.0 |
double n = 1.0; |
dconst_1 dstore_18 |
|
ldc2_w |
从常量池加载 double | 超出dconst 范围的 double |
double o = 3.1415; |
ldc2_w #5 dstore_20 |
|
字符串常量 | ldc |
从常量池加载字符串 | 所有字符串常量 | String p = "hello"; |
ldc #6 astore_22 |
1.2、从局部变量表加载到操作数栈
数据类型 | 简化指令(索引 0~3) | 通用指令(任意索引) | 作用 | Java 代码示例 | 字节码示例 |
---|---|---|---|---|---|
int | iload_1 |
iload <n> |
加载 int 变量 | int q = d; (d 在索引 4) |
iload_4 istore_23 |
long | lload_1 |
lload <n> |
加载 long 变量 | long r = i; (i 在索引 11) |
lload 11 lstore_24 |
float | fload_2 |
fload <n> |
加载 float 变量 | float s = l; (l 在索引 15) |
fload_15 fstore_26 |
double | dload_3 |
dload <n> |
加载 double 变量 | double t = o; (o 在索引 20) |
dload 20 dstore_27 |
引用类型 | aload_0 |
aload <n> |
加载对象引用(如this ) |
Object u = this; |
aload_0 astore_29 |
引用类型 | aload_1 |
aload <n> |
加载对象引用 | String v = p; (p 在索引 22) |
aload_22 astore_30 |
1.3、从操作数栈存储到局部变量表
数据类型 | 简化指令(索引 0~3) | 通用指令(任意索引) | 作用 | Java 代码示例 | 字节码示例 |
---|---|---|---|---|---|
int | istore_1 |
istore <n> |
存储 int 值 | int w = 10; |
bipush 10 istore_31 |
long | lstore_2 |
lstore <n> |
存储 long 值 | long x = 100000L; |
ldc2_w #7 lstore 32 |
float | fstore_3 |
fstore <n> |
存储 float 值 | float y = 5.5f; |
ldc #8 fstore_34 |
double | dstore_0 |
dstore <n> |
存储 double 值 | double z = 9.9; |
ldc2_w #9 dstore_35 |
引用类型 | astore_1 |
astore <n> |
存储对象引用 | Object obj = new Object(); |
new #10 dup invokespecial #11 astore_37 |
1.4、宽索引指令
指令 | 作用 | 说明 | Java 代码示例 | 字节码示例 |
---|---|---|---|---|
wide |
扩展局部变量表索引范围 | 支持索引≥256 的变量 | int arr[] = new int[300]; int val = arr[256]; (假设 val 在索引 256) |
wide iload 256 istore 38 |
二、运算指令
2.1、算术运算指令(对操作数栈中的数值执行算术操作)
数据类型 | 指令 | 作用 | 说明 | Java 代码示例 | 字节码示例 |
---|---|---|---|---|---|
int | iadd |
加法 | 栈顶两 int 相加,结果入栈 | int a = 2 + 3; |
iconst_2 iconst_3 iadd istore_1 |
isub |
减法 | 栈顶两 int 相减,结果入栈 | int b = 5 - 1; |
iconst_5 iconst_1 isub istore_2 |
|
imul |
乘法 | 栈顶两 int 相乘,结果入栈 | int c = 3 * 4; |
iconst_3 iconst_4 imul istore_3 |
|
idiv |
除法 | 栈顶两 int 相除,结果入栈 | int d = 10 / 2; |
bipush 10 iconst_2 idiv istore_4 |
|
irem |
取余 | 栈顶两 int 取余,结果入栈 | int e = 7 % 3; |
bipush 7 iconst_3 irem istore_5 |
|
ineg |
取反 | 栈顶 int 取相反数,结果入栈 | int f = -a; |
iload_1 ineg istore_6 |
|
long | ladd |
加法 | 栈顶两 long 相加,结果入栈 | long g = 100L + 200L; |
ldc2_w #2 ldc2_w #3 ladd lstore_7 |
lsub |
减法 | 栈顶两 long 相减,结果入栈 | long h = 500L - 150L; |
ldc2_w #4 ldc2_w #5 lsub lstore_9 |
|
lmul |
乘法 | 栈顶两 long 相乘,结果入栈 | long i = 10L * 30L; |
lconst_10 ldc2_w #6 lmul lstore_11 |
|
float | fadd |
加法 | 栈顶两 float 相加,结果入栈 | float j = 2.5f + 1.5f; |
ldc #7 ldc #8 fadd fstore_13 |
fsub |
减法 | 栈顶两 float 相减,结果入栈 | float k = 5.0f - 2.3f; |
fconst_5 ldc #9 fsub fstore_14 |
|
double | dadd |
加法 | 栈顶两 double 相加,结果入栈 | double l = 3.14 + 2.71; |
ldc2_w #10 ldc2_w #11 dadd dstore_15 |
ddiv |
除法 | 栈顶两 double 相除,结果入栈 | double m = 10.0 / 3.0; |
ldc2_w #12 ldc2_w #13 ddiv dstore_17 |
2.2、位运算指令(对操作数栈中的整数执行位操作)
数据类型 | 指令 | 作用 | 说明 | Java 代码示例 | 字节码示例 | |
---|---|---|---|---|---|---|
int | ishl |
左移 | 栈顶两 int,低位移高,结果入栈 | int n = 8 << 2; |
bipush 8 iconst_2 ishl istore_19 |
|
ishr |
算术右移 | 带符号右移,高位补符号位 | int o = -8 >> 2; |
bipush -8 iconst_2 ishr istore_20 |
||
iushr |
逻辑右移 | 无符号右移,高位补 0 | int p = 8 >>> 2; |
bipush 8 iconst_2 iushr istore_21 |
||
iand |
按位与 | 栈顶两 int 按位与,结果入栈 | int q = 3 & 5; |
iconst_3 iconst_5 iand istore_22 |
||
ior |
按位或 | 栈顶两 int 按位或,结果入栈 | `int r = 3 | 5;` | iconst_3 iconst_5 ior istore_23 |
|
ixor |
按位异或 | 栈顶两 int 按位异或,结果入栈 | int s = 3 ^ 5; |
iconst_3 iconst_5 ixor istore_24 |
||
long | lshl |
左移 | 栈顶两 long 左移,结果入栈 | long t = 4L << 3; |
lconst_4 iconst_3 lshl lstore_25 |
|
land |
按位与 | 栈顶两 long 按位与,结果入栈 | long u = 0x0FL & 0xF0L; |
ldc2_w #14 ldc2_w #15 land lstore_27 |
2.3、比较运算指令(比较操作数栈中的值,结果用于控制流转)
数据类型 | 指令 | 作用 | 说明 | Java 代码示例 | 字节码示例 |
---|---|---|---|---|---|
int | if_icmpeq |
相等则跳转 | 比较两 int,相等则跳转到指定偏移量 | if(a == b) { ... } |
iload_1 iload_2 if_icmpeq 30 |
if_icmpne |
不等则跳转 | 比较两 int,不等则跳转 | if(a != b) { ... } |
iload_1 iload_2 if_icmpne 40 |
|
if_icmplt |
小于则跳转 | 比较两 int,前者小于后者则跳转 | if(a < b) { ... } |
iload_1 iload_2 if_icmplt 50 |
|
if_icmpgt |
大于则跳转 | 比较两 int,前者大于后者则跳转 | if(a > b) { ... } |
iload_1 iload_2 if_icmpgt 60 |
|
long | lcmpeq |
相等则跳转 | 比较两 long,相等则跳转 | if(g == h) { ... } |
lload_7 lload_9 lcmpeq 70 |
float | fcmpl |
比较后压栈 | 比较两 float,结果(-1/0/1)入栈(NaN 视为小于) | if(j < k) { ... } |
fload_13 fload_14 fcmpl iflt 80 |
fcmpg |
比较后压栈 | 比较两 float,结果(-1/0/1)入栈(NaN 视为大于) | if(j > k) { ... } |
fload_13 fload_14 fcmpg ifgt 90 |
|
引用类型 | if_acmpeq |
引用相等则跳转 | 比较两对象引用,地址相同则跳转 | if(obj1 == obj2) { ... } |
aload_28 aload_29 if_acmpeq 100 |
if_acmpne |
引用不等则跳转 | 比较两对象引用,地址不同则跳转 | if(obj1 != obj2) { ... } |
aload_28 aload_29 if_acmpne 110 |
三、对象操作指令
3.1、对象创建与初始化指令
指令 | 作用 | 说明 | Java 代码示例 | 字节码示例 |
---|---|---|---|---|
new |
创建类实例 | 在堆中分配对象实例空间,返回对象引用(未初始化) | Person p = new Person(); |
new #2 <Person> dup invokespecial #3 <Person.<init>> astore_1 |
invokespecial |
调用构造方法 | 用于初始化对象(调用<init> 方法) |
隐含在new 表达式中 |
同上(invokespecial 为构造方法调用) |
3.2、字段访问指令
指令 | 作用 | 说明 | Java 代码示例 | 字节码示例 |
---|---|---|---|---|
getfield |
获取对象实例字段值 | 从对象中读取实例变量的值 | String name = p.name; |
aload_1 getfield #4 <Person.name> astore_2 |
putfield |
设置对象实例字段值 | 向对象的实例变量写入值 | p.age = 20; |
aload_1 bipush 20 putfield #5 <Person.age> |
getstatic |
获取类静态字段值 | 读取类的静态变量(类级变量) | int count = Person.total; |
getstatic #6 <Person.total> istore_3 |
putstatic |
设置类静态字段值 | 写入类的静态变量 | Person.total = 100; |
bipush 100 putstatic #6 <Person.total> |
3.3、数组操作指令
指令 | 作用 | 说明 | Java 代码示例 | 字节码示例 |
---|---|---|---|---|
newarray |
创建基本类型数组 | 用于创建 int、float 等基本类型数组 | int[] arr = new int[5]; |
iconst_5 newarray int astore_4 |
anewarray |
创建引用类型数组 | 用于创建对象数组(如 String []) | String[] strs = new String[3]; |
iconst_3 anewarray #7 <java/lang/String> astore_5 |
multianewarray |
创建多维数组 | 用于创建二维及以上数组 | int[][] matrix = new int[2][3]; |
iconst_2 iconst_3 multianewarray #8 <[[I> 2 astore_6 |
arraylength |
获取数组长度 | 将数组长度压入操作数栈 | int len = arr.length; |
aload_4 arraylength istore_7 |
iaload |
读取 int 数组元素 | 从 int 数组指定索引读取值 | int val = arr[0]; |
aload_4 iconst_0 iaload istore_8 |
iastore |
写入 int 数组元素 | 向 int 数组指定索引写入值 | arr[1] = 100; |
aload_4 iconst_1 bipush 100 iastore |
aaload |
读取引用数组元素 | 从对象数组指定索引读取引用 | String s = strs[0]; |
aload_5 iconst_0 aaload astore_9 |
aastore |
写入引用数组元素 | 向对象数组指定索引写入引用 | strs[1] = "hello"; |
aload_5 iconst_1 ldc #9 <hello> aastore |
3.4、类型检查指令
指令 | 作用 | 说明 | Java 代码示例 | 字节码示例 |
---|---|---|---|---|
instanceof |
检查对象类型 | 判断对象是否为指定类的实例,结果(1/0)入栈 | boolean isPerson = obj instanceof Person; |
aload_10 instanceof #2 <Person> istore_11 |
checkcast |
类型转换检查 | 确保对象可转换为目标类型,失败抛 ClassCastException | Person p2 = (Person) obj; |
aload_10 checkcast #2 <Person> astore_12 |
四、方法调用与返回指令
4.1、方法调用指令
指令 | 作用 | 说明 | Java 代码示例 | 字节码示例 |
---|---|---|---|---|
invokestatic |
调用静态方法 | 调用类的静态方法(无实例参与),属于静态绑定 | Math.max(3, 5); |
iconst_3 iconst_5 invokestatic #2 <java/lang/Math.max> |
invokespecial |
调用特殊方法 | 用于调用构造方法(<init> )、私有方法、父类方法,属于静态绑定 |
super(); (构造方法中) |
aload_0 invokespecial #3 <java/lang/Object.<init>> |
this.privateMethod(); |
aload_0 invokespecial #4 <Person.privateMethod> |
|||
invokevirtual |
调用实例方法 | 调用对象的实例方法(非私有、非构造方法),支持动态绑定(多态) | p.getName(); |
aload_1 invokevirtual #5 <Person.getName> |
invokeinterface |
调用接口方法 | 调用接口中定义的方法,动态绑定到实现类 | list.add("item"); |
aload_2 ldc #6 <item> invokeinterface #7 <java/util/List.add> 2 |
invokedynamic |
调用动态方法 | 支持动态语言特性(如 Lambda 表达式),绑定逻辑由引导方法决定 | Runnable r = () -> {}; |
invokedynamic #8 <run, BootstrapMethod #0> |
4.2、方法返回指令
指令 | 作用 | 说明 | Java 代码示例 | 字节码示例 |
---|---|---|---|---|
return |
无返回值返回 | 用于void 方法,无值返回 |
void greet() { return; } |
return |
ireturn |
返回 int 类型 | 从方法返回 int 值(包括 boolean、byte、char、short 的包装返回) | int getAge() { return 20; } |
bipush 20 ireturn |
lreturn |
返回 long 类型 | 从方法返回 long 值 | long getTimestamp() { return 123456L; } |
ldc2_w #9 lreturn |
freturn |
返回 float 类型 | 从方法返回 float 值 | float getScore() { return 95.5f; } |
ldc #10 freturn |
dreturn |
返回 double 类型 | 从方法返回 double 值 | double getPrice() { return 19.99; } |
ldc2_w #11 dreturn |
areturn |
返回引用类型 | 从方法返回对象或数组引用 | String getName() { return name; } |
aload_0 getfield #12 <Person.name> areturn |
五、控制转移指令
5.1、条件分支指令(基于比较结果跳转)
指令 | 作用 | 说明 | Java 代码示例 | 字节码示例 |
---|---|---|---|---|
int 值比较 | if_icmpeq |
两 int 相等则跳转 | if(a == b) { ... } |
iload_1 iload_2 if_icmpeq 20 |
if_icmpne |
两 int 不等则跳转 | if(a != b) { ... } |
iload_1 iload_2 if_icmpne 30 |
|
if_icmplt |
前 int < 后 int 则跳转 | if(a < b) { ... } |
iload_1 iload_2 if_icmplt 40 |
|
if_icmpgt |
前 int > 后 int 则跳转 | if(a > b) { ... } |
iload_1 iload_2 if_icmpgt 50 |
|
if_icmple |
前 int <= 后 int 则跳转 | if(a <= b) { ... } |
iload_1 iload_2 if_icmple 60 |
|
if_icmpge |
前 int >= 后 int 则跳转 | if(a >= b) { ... } |
iload_1 iload_2 if_icmpge 70 |
|
引用比较 | if_acmpeq |
两引用相等则跳转 | if(obj1 == obj2) { ... } |
aload_3 aload_4 if_acmpeq 80 |
if_acmpne |
两引用不等则跳转 | if(obj1 != obj2) { ... } |
aload_3 aload_4 if_acmpne 90 |
|
栈顶值判断 | ifeq |
栈顶 int 为 0 则跳转 | if(flag == 0) { ... } |
iload_5 ifeq 100 |
ifne |
栈顶 int 不为 0 则跳转 | if(flag != 0) { ... } |
iload_5 ifne 110 |
|
iflt |
栈顶 int < 0 则跳转 | if(count < 0) { ... } |
iload_6 iflt 120 |
|
ifgt |
栈顶 int > 0 则跳转 | if(count > 0) { ... } |
iload_6 ifgt 130 |
|
null 判断 | ifnull |
引用为 null 则跳转 | if(obj == null) { ... } |
aload_3 ifnull 140 |
ifnonnull |
引用非 null 则跳转 | if(obj != null) { ... } |
aload_3 ifnonnull 150 |
5.2、无条件分支指令(直接跳转)
指令 | 作用 | 说明 | Java 代码示例 | 字节码示例 |
---|---|---|---|---|
goto |
无条件跳转到指定偏移量 | 短偏移量跳转(16 位偏移) | loop: { ...; goto loop; } |
goto 5 (跳转到偏移量 5) |
goto_w |
无条件跳转到宽偏移量 | 长偏移量跳转(32 位偏移,支持更大范围) | 大型循环或跳转距离远时 | goto_w 1000 (跳转到偏移量 1000) |
5.3、多分支跳转指令(switch 语句专用)
指令 | 作用 | 说明 | Java 代码示例 | 字节码示例 |
---|---|---|---|---|
tableswitch |
连续 case 值的多分支跳转 | 适用于 case 值连续的 switch,通过索引表快速定位 | switch(a) { case 1: ...; case 2: ...; } |
tableswitch 1: 20 2: 30 default: 40 |
lookupswitch |
离散 case 值的多分支跳转 | 适用于 case 值不连续的 switch,通过查找表匹配 | switch(b) { case 10: ...; case 200: ...; } |
lookupswitch 10: 50 200: 60 default: 70 |
5.4、异常处理指令
指令 | 作用 | 说明 | Java 代码示例 | 字节码示例 |
---|---|---|---|---|
athrow |
抛出异常 | 将操作数栈顶的异常对象抛出 | throw new Exception(); |
new #8 <java/lang/Exception> dup invokespecial #9 <Exception.<init>> athrow |
六、栈操作与同步指令
6.1、栈操作指令(直接操作操作数栈)
指令 | 作用 | 说明 | Java 代码示例 | 字节码示例 |
---|---|---|---|---|
pop |
弹出栈顶 1 个元素 | 用于清理操作数栈中不再使用的单元素(如 int、float、引用) | 临时变量运算后清理 | iconst_1 iconst_2 iadd pop (丢弃结果) |
pop2 |
弹出栈顶 2 个元素 | 用于清理占 2 个 Slot 的元素(long、double)或连续 2 个单元素 | 清理 long 类型临时值 | lconst_1 pop2 (丢弃 long 值) |
dup |
复制栈顶 1 个元素并压入栈 | 复制单元素(如 int、引用),栈深度 + 1 | 对象创建时复制引用 | new #2 <Person> dup (复制对象引用)invokespecial #3 <Person.<init>> |
dup_x1 |
复制栈顶元素并插入到下方第 2 个元素前 | 调整栈结构,复制后顺序:[原栈顶 - 1, 复制值,原栈顶] | 复杂运算时调整操作数顺序 | iconst_1 iconst_2 dup_x1 (栈变为 [1,2,1]) |
dup_x2 |
复制栈顶元素并插入到下方第 3 个元素前 | 支持下方是单元素或 long/double(占 2 个 Slot) | 多操作数调整 | iconst_1 iconst_2 iconst_3 dup_x2 (栈变为 [1,3,2,3]) |
dup2 |
复制栈顶 2 个元素并压入栈 | 复制 long/double 或两个单元素,栈深度 + 2 | 复制 long 类型值 | lconst_1 dup2 (栈变为 [1L,1L]) |
dup2_x1 |
复制栈顶 2 个元素并插入到下方第 3 个元素前 | 调整包含 long/double 的栈结构 | 复杂 long 运算调整 | lconst_1 iconst_2 dup2_x1 (栈变为 [1L,2,1L]) |
dup2_x2 |
复制栈顶 2 个元素并插入到下方第 4 个元素前 | 最灵活的双元素复制指令 | 多类型混合调整 | iconst_1 lconst_2 dup2_x2 (栈变为 [1,2L,1,2L]) |
swap |
交换栈顶两个单元素 | 仅用于两个单元素(如 int、引用),不支持 long/double | 交换操作数顺序 | iconst_1 iconst_2 swap (栈变为 [2,1]) |
6.2、同步指令(实现 synchronized 同步)
指令 | 作用 | 说明 | Java 代码示例 | 字节码示例 |
---|---|---|---|---|
monitorenter |
获取对象监视器锁 | 进入同步块时获取锁,同一时间仅一个线程可获取 | synchronized(obj) { ... } |
aload_1 monitorenter |
monitorexit |
释放对象监视器锁 | 退出同步块时释放锁,确保锁最终会被释放(包括异常路径) | 同步块结束处 | monitorexit |