一个理解JVM的例子2
import java.util.*;
public class LocalDemo {
private List<String> data = new ArrayList<>();
public void someMethod(String param) {
List<String> data = this.data;
if (data != null && data.size() > 0 && data.contains(param)) {
System.out.println(data.indexOf(param));
}
}
}
使用javac编译
javac LocalDemo.java
编译后生成class文件: "LocalDemo.class"
(生成的class文件实际就是Java bytecode)
使用javap反汇编class文件
javap -c LocalDemo
反汇编结果:
Compiled from "LocalDemo.java"
public class LocalDemo {
public LocalDemo();
Code:
0: aload_0
1: invokespecial #1 // Method java/lang/Object."<init>":()V
4: aload_0
5: new #2 // class java/util/ArrayList
8: dup
9: invokespecial #3 // Method java/util/ArrayList."<init>":()V
12: putfield #4 // Field data:Ljava/util/List;
15: return
public void someMethod(java.lang.String);
Code:
0: aload_0
1: getfield #4 // Field data:Ljava/util/List;
4: astore_2
5: aload_2
6: ifnull 41
9: aload_2
10: invokeinterface #5, 1 // InterfaceMethod java/util/List.size:()I
15: ifle 41
18: aload_2
19: aload_1
20: invokeinterface #6, 2 // InterfaceMethod java/util/List.contains:(Ljava/lang/Object;)Z
25: ifeq 41
28: getstatic #7 // Field java/lang/System.out:Ljava/io/PrintStream;
31: aload_2
32: aload_1
33: invokeinterface #8, 2 // InterfaceMethod java/util/List.indexOf:(Ljava/lang/Object;)I
38: invokevirtual #9 // Method java/io/PrintStream.println:(I)V
41: return
}
结果分析
Compiled from "LocalDemo.java"
public class LocalDemo {
public LocalDemo();
Code:
0: aload_0
1: invokespecial #1 // Method java/lang/Object."<init>":()V
4: aload_0
5: new #2 // class java/util/ArrayList
8: dup
9: invokespecial #3 // Method java/util/ArrayList."<init>":()V
12: putfield #4 // Field data:Ljava/util/List;
15: return
public void someMethod(java.lang.String);
Code:
0: aload_0
1: getfield #4 // Field data:Ljava/util/List;
4: astore_2
5: aload_2
6: ifnull 41
9: aload_2
10: invokeinterface #5, 1 // InterfaceMethod java/util/List.size:()I
15: ifle 41
18: aload_2
19: aload_1
20: invokeinterface #6, 2 // InterfaceMethod java/util/List.contains:(Ljava/lang/Object;)Z
25: ifeq 41
28: getstatic #7 // Field java/lang/System.out:Ljava/io/PrintStream;
31: aload_2
32: aload_1
33: invokeinterface #8, 2 // InterfaceMethod java/util/List.indexOf:(Ljava/lang/Object;)I
38: invokevirtual #9 // Method java/io/PrintStream.println:(I)V
41: return
}
修改Java程序:LocalDemo.java
import java.util.*;
public class LocalDemo {
private List<String> data = new ArrayList<>();
public void someMethod(String param) {
//List<String> data = this.data;
if (data != null && data.size() > 0 && data.contains(param)) {
System.out.println(data.indexOf(param));
}
}
}
再次编译和反汇编结果如下
Compiled from "LocalDemo.java"
public class LocalDemo {
public LocalDemo();
Code:
0: aload_0
1: invokespecial #1 // Method java/lang/Object."<init>":()V
4: aload_0
5: new #2 // class java/util/ArrayList
8: dup
9: invokespecial #3 // Method java/util/ArrayList."<init>":()V
12: putfield #4 // Field data:Ljava/util/List;
15: return
public void someMethod(java.lang.String);
Code:
0: aload_0
1: getfield #4 // Field data:Ljava/util/List;
#getfield 表示获取对象的成员变量值(在这里的成员变量是data)
4: ifnull 48
7: aload_0
8: getfield #4 // Field data:Ljava/util/List;
11: invokeinterface #5, 1 // InterfaceMethod java/util/List.size:()I
16: ifle 48
19: aload_0
20: getfield #4 // Field data:Ljava/util/List;
23: aload_1
24: invokeinterface #6, 2 // InterfaceMethod java/util/List.contains:(Ljava/lang/Object;)Z
29: ifeq 48
32: getstatic #7 // Field java/lang/System.out:Ljava/io/PrintStream;
35: aload_0
36: getfield #4 // Field data:Ljava/util/List;
39: aload_1
40: invokeinterface #8, 2 // InterfaceMethod java/util/List.indexOf:(Ljava/lang/Object;)I
45: invokevirtual #9 // Method java/io/PrintStream.println:(I)V
48: return
}