Java class文件格式之常量池

上传人:ji****72 文档编号:46537678 上传时间:2018-06-27 格式:PDF 页数:8 大小:725.85KB
返回 下载 相关 举报
Java class文件格式之常量池_第1页
第1页 / 共8页
Java class文件格式之常量池_第2页
第2页 / 共8页
Java class文件格式之常量池_第3页
第3页 / 共8页
Java class文件格式之常量池_第4页
第4页 / 共8页
Java class文件格式之常量池_第5页
第5页 / 共8页
点击查看更多>>
资源描述

《Java class文件格式之常量池》由会员分享,可在线阅读,更多相关《Java class文件格式之常量池(8页珍藏版)》请在金锄头文库上搜索。

1、 1 / 8 Java class 文件格式之常量池 常量池中各数据项类型详解 常量池中的数据项是通过索引来引用的, 常量池中的各个数据项之间也会相互引用。在这 11 中常量池数据项类型中, 有两种比较基础, 之所以说它们基础, 是因为这两种类型的数据项会被其他类型的数据项引用。 这两种数据类型就是CONSTANT_Utf8 和 CONSTANT_NameAndType , 其中 CONSTANT_NameAndType 类型的数据项(CONSTANT_NameAndType_info)也会引用 CONSTANT_Utf8 类型的数据项(CONSTANT_Utf8_info) 。 与其他介绍常

2、量池的书籍或其他资料不同, 本着循序渐进和先后分明的原则, 我们首先对这两种比较基本的类型的数据项进行介绍, 然后再依次介绍其他 9 中数据项。 (1) CONSTANT_Utf8_info 一个 CONSTANT_Utf8_info 是一个 CONSTANT_Utf8 类型的常量池数据项, 它存储的是一个常量字符串。 常量池中的所有字面量几乎都是通过 CONSTANT_Utf8_info 描述的。下面我们首先讲解 CONSTANT_Utf8_info 数据项的存储格式。在前面的文章中, 我们提到, 常量池中数据项的类型由一个整型的标志值(tag)决定, 所以所有常量池类型的 info中都必须

3、有一个 tag 信息, 并且这个 tag 值位于数据项的第一个字节上。 一个 11 中常量池数据类型, 所以就有 11 个 tag值表示这 11 中类型。而 CONSTANT_Utf8_info 的 tag 值为 1, 也就是说如果虚拟机要解析一个常量池数据项, 首先去读这个数据项的第一个字节的 tag 值, 如果这个 tag 值为 1, 那么就说明这个数据项是一个 CONSTANT_Utf8 类型的数据项。 紧挨着 tag 值的两个字节是存储的字符串的长度 length, 剩下的字节就存储着字符串。 所以, 它的格式是这样的: 其中 tag 占一个字节, length 占 2 个字节, by

4、tes 代表存储的字符串, 占 length 字节。所以, 如果这个CONSTANT_Utf8_info 存储的是字符串“Hello“, 那么他的存储形式是这样的: 2 / 8 现在我们知道了 CONSTANT_Utf8_info 数据项的存储形式, 那么 CONSTANT_Utf8_info 数据项都存储了什么字符串呢? CONSTANT_Utf8_info 可包括的字符串主要以下这些: 程序中的字符串常量 常量池所在当前类(包括接口和枚举)的全限定名 常量池所在当前类的直接父类的全限定名 常量池所在当前类型所实现或继承的所有接口的全限定名 常量池所在当前类型中所定义的字段的名称和描述符 常

5、量池所在当前类型中所定义的方法的名称和描述符 由当前类所引用的类型的全限定名 由当前类所引用的其他类中的字段的名称和描述符 由当前类所引用的其他类中的方法的名称和描述符 与当前 class 文件中的属性相关的字符串, 如属性名等 总结一下, 其中有这么五类: 程序中的字符串常量, 类型的全限定名, 方法和字段的名称, 方法和字段的描述符, 属性相关字符串。 程序中的字符串常量不用多说了, 我们经常使用它们创建字符串对象, 属性相关的字符串, 等到讲到 class 中的属性信息 (attibute) 时自会提及。 方法和字段的名称也不用多说了 。 剩下的就是类型的全限定名,方法和字段的描述符 。

6、 还有一点需要说明, 类型的全限定名, 方法和字段的名称, 方法和字段的描述符, 可以是本类型中定义的, 也可能是本类中引用的其他类的。 下面我们通过一个例子来进行说明。 示例源码: 1. package com.bjpowernode.test; 2. 3. public class Programer extends Person 4. 5. static String company = “CompanyA“; 6. 7. static 8. System.out.println(“staitc init“); 9. 10. 11. 12. String position; 13. Co

7、mputer computer; 14. 15. public Programer() 16. this.position = “engineer“; 17. puter = new Computer(); 18. 19. 20. public void working() 3 / 8 21. System.out.println(“coding.“); 22. computer.working(); 23. 24. 别看这个类简单, 但是反编译后, 它的常量池有 53 项之多。 在这 53 项常量池数据项中, 各种类型的数据项都有, 当然也包括不少的 CONSTANT_Utf8_info 。

8、 下面只列出反编译后常量池中的 CONSTANT_Utf8_info 数据项: 1. #2 = Utf8 com/jg/zhang/Programer /当前类的全限定名 2. #4 = Utf8 com/jg/zhang/Person /父类的全限定名 3. #5 = Utf8 company /company 字段的名称 4. #6 = Utf8 Ljava/lang/String; /company 和 position 字段的描述符 5. #7 = Utf8 position /position 字段的名称 6. #8 = Utf8 computer /computer 字段的名称 7

9、. #9 = Utf8 Lcom/jg/zhang/Computer; /computer 字段的描述符 8. #10 = Utf8 /类初始化方法(即静态初始化块)的方法名 9. #11 = Utf8 ()V /working 方法的描述符 10. #12 = Utf8 Code /Code 属性的属性名 11. #14 = Utf8 CompanyA /程序中的常量字符串 12. #19 = Utf8 java/lang/System /所引用的 System 类的全限定名 13. #21 = Utf8 out /所引用的 out 字段的字段名 14. #22 = Utf8 Ljava/i

10、o/PrintStream; /所引用的 out 字段的描述符 15. #24 = Utf8 staitc init /程序中的常量字符串 16. #27 = Utf8 java/io/PrintStream /所引用的 PrintStream 类的全限定名 17. #29 = Utf8 println /所引用的 println 方法的方法名 18. #30 = Utf8 (Ljava/lang/String;)V /所引用的 println 方法的描述符 19. #31 = Utf8 LineNumberTable /LineNumberTable 属性的属性名 20. #32 = Utf

11、8 LocalVariableTable /LocalVariableTable 属性的属性名 21. #33 = Utf8 /当前类的构造方法的方法名 22. #41 = Utf8 com/jg/zhang/Computer /所引用的 Computer 类的全限定名 23. #45 = Utf8 this /局部变量 this 的变量名 24. #46 = Utf8 Lcom/jg/zhang/Programer; /局部变量 this 的描述符 25. #47 = Utf8 working /woking 方法的方法名 26. #49 = Utf8 coding. /程序中的字符串常量

12、27. #52 = Utf8 SourceFile /SourceFile 属性的属性名 28. #53 = Utf8 Programer.java /当前类所在的源文件的文件名 4 / 8 上面只列出了反编译结果中常量池中的 CONSTANT_Utf8_info 数据项。 其中第三列不是 javap 反编译的输出结果, 而是我加上的注释。 读者可以对比上面的程序源码来看一下, 这样的话, 就可以清楚的看出, 源文件中的各种字符串, 是如何和存放到 CONSTANT_Utf8_info 中的。 这里要强调一下, 源文件中的几乎所有可见的字符串都存放在 CONSTANT_Utf8_info 中, 其他类型的常量池项只不过是对 CONSTANT_Utf8_info 的引用。 其他常量池项, 把引用的 CONSTANT_Utf8_info 组合起来, 进而可以描述更多的信息。 下面将要介绍的 CONSTANT_NameAndType_info 就可以验证这个结论。 (2) CONSTANT_NameAndType 类型的数据项 常量池中的一个 CONSTANT_NameAndType_info 数据项, 可以看做 CONSTANT_NameA

展开阅读全文
相关资源
相关搜索

当前位置:首页 > 行业资料 > 其它行业文档

电脑版 |金锄头文库版权所有
经营许可证:蜀ICP备13022795号 | 川公网安备 51140202000112号