一、概述
方法表集合与属性表集合的结构类似,是对方法的修饰符、返回类型、方法名、参数个数、参数类型、方法体的描述集合。
编辑
方法表集合的结构是一个类似于数组的结构,JVM在对java文件进行编译时,会将类中的方法个数放到方法计数器中,然后将每个方法组成method_info结构,依次存在在方法计数器之后。
二、方法表集合的构成
方法表集合的结构与字段表结构非常的类似,开头也是用了两个字节表示方法的个数,然后接着是每个方法的描述。
1.方法计数器
方法表集合是由很多method_info组成的,所以方法表集合的前两个字节表示有多少个方法,占两个字节,16位。
2.method_info
method_info{ access_flag;//访问修饰符 name_index;//方法名称(这里是常量池中的index) descriptor_index;//参数的类型以及返回值得类型(同样指向常量池得编号) attributes_count;//属性个数 attibutes;//属性表(这里得属性个数及属性表都放在属性表中得‘Code’属性里面) }
编辑
3.access_flags
与属性表集合的相同,这里不再重复,请参考《JVM虚拟机-Class文件之字段表集合》相关部分内容。
4.name_index和descriptor_index
name_index和descriptor_index,是对常量池的引用,name_index指字段的简单名称,descriptor_index指字段描述符。
descriptor_index描述符用来描述方法的参数列表(包括数量,类型以及顺序)和返回值.根据描述符规则,无返回值的void类型都用一个大写字符来表示。
三、实例拆解
定义一个类:
public class HelloWord{ public Object test(){return null;} }
字节码文件:
编辑
public class com.csdn.reader.HelloWord minor version: 0 major version: 52 flags: ACC_PUBLIC, ACC_SUPER Constant pool: #1 = Methodref #3.#15 // java/lang/Object."<init>":()V #2 = Class #16 // com/csdn/reader/HelloWord #3 = Class #17 // java/lang/Object #4 = Utf8 <init> #5 = Utf8 ()V #6 = Utf8 Code #7 = Utf8 LineNumberTable #8 = Utf8 LocalVariableTable #9 = Utf8 this #10 = Utf8 Lcom/csdn/reader/HelloWord; #11 = Utf8 test #12 = Utf8 ()Ljava/lang/Object; #13 = Utf8 SourceFile #14 = Utf8 HelloWord.java #15 = NameAndType #4:#5 // "<init>":()V #16 = Utf8 com/csdn/reader/HelloWord #17 = Utf8 java/lang/Object { public com.csdn.reader.HelloWord(); descriptor: ()V flags: ACC_PUBLIC Code: stack=1, locals=1, args_size=1 0: aload_0 1: invokespecial #1 // Method java/lang/Object."<init>":()V 4: return LineNumberTable: line 3: 0 LocalVariableTable: Start Length Slot Name Signature 0 5 0 this Lcom/csdn/reader/HelloWord; public java.lang.Object test(); descriptor: ()Ljava/lang/Object; flags: ACC_PUBLIC Code: stack=1, locals=1, args_size=1 0: aconst_null 1: areturn LineNumberTable: line 4: 0 LocalVariableTable: Start Length Slot Name Signature 0 2 0 this Lcom/csdn/reader/HelloWord; } SourceFile: "HelloWord.java"
方法解析:
编辑
编辑
四、总结
方法表集合中不会列出从父类或者父接口中继承而来的方法,但有可能列出原来Java代码中不存在的方法,比如无参构造方法。
参考资料: