[java虚拟机]--(2)字节码文件--(3)常量池

声明:
    Author:赵志乾
    Date:2018-6-18
    Declaration:All Right Reserved!!!

背景知识:

常量池这一概念在虚拟机内存章节中也提到过(《虚拟机内存》)。虚拟机内存中的常量池位于方法区内,其全称为运行时常量池。之所以称为运行时常量池,是因为其伴随虚拟机的运行而存在,具有动态性,即随时间的推移,会有新的内容加入,也有新的内容被gc线程回收。而字节码文件中的常量池则是一个静态概念,其内容不会随时间发生变动。

 

字节码文件中的常量池

1、静态常量池紧随文件版本号,是字节码文件中的第一个表类型数据。其作为文件中的资源仓库,为其他内容提供了各种索引信息。

静态常量池的大小随文件而不同,故在其入口处放置一容器计数器,以表征当前文件中静态常量池的大小。而池内存放的内容大体上可分为两大类:字面常量和符号引用。

静态常量池本身是一个表类型数据,并且其存放的每一个数据项也是一个表类型数据。最无语的是这些数据项共有14种类型,且结构各不相同。不过每一数据项的起始都会有一个标志位tag,来表征其属于哪一种常量类型。

 

补充内容:(2018-10-9)

1、常量池中存放常量,但并不是所有的常量都存放于常量池。

这一点需要从常量池的作用谈起。在信息包含层面上,可以将常量池看作是资源注册表,如各种类型、标识等;在功能层面上,可以将常量池看作是引用的转换媒介,如在语句中使用的各种标识、类型等,只需要使用其在常量池中的索引便可引用,从而为各种常量提供统一的访问方式。

其次要从常量的种类谈起。常量有很多种类,光常量池中可存放的就有14种。除此之外,还有数值型字面常量,布尔值字面常量等,也就是说数值型字面常量和布尔值字面常量是不放在常量池中的。

2、数值型字面常量和布尔值字面常量为什么不放到常量池中?

布尔值字面常量在底层实际上会转化为数值型字面常量,即所谓的true和false是编译器为开发人员提供的语法糖。因此,我们只讨论数值型字面常量即可。

数值型字面常量相对于其他种类的常量,有其自身的特殊性:短小。如果将数值型字面常量布局到常量池,从空间角度来看:语句中还需要存放所需常量在常量池中的索引,以便完成引用的转换,而索引本身占用的大小和数值型字面常量相比又相差无几,势必会带来空间消耗的倍增;从时间角度来看:语句在执行过程中,需要通过所需常量在常量池中的索引完成到常量具体内容的转化,而这一过程是需要消耗额外的CPU时钟周期的。所以,基于时空双重角度的考虑,将数值型字面常量直接放置在指令语句中,作为立即数来使用,而不是将其放到常量池中。

 

 

 

邮箱:zhaozhiqian001@163.com

参考资料:《深入理解Java虚拟机》--周志明

  • 1
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 打赏
    打赏
  • 3
    评论
评论 3
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包

打赏作者

我叫白小猿

你的鼓励将是我创作的最大动力

¥1 ¥2 ¥4 ¥6 ¥10 ¥20
扫码支付:¥1
获取中
扫码支付

您的余额不足,请更换扫码支付或充值

打赏作者

实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值