关闭

常量池技术

753人阅读 评论(0) 收藏 举报

 

 

2.1 程序计数器寄存器(The pc Register)

2.2 栈

JVM为每个新创建的线程都分配一个栈.也就是说,对于一个Java程序来说,它的运行就是通过对栈的操作来完成的。它用来保存局部变量的值,包括:1.用来保存基本数据类型的值;2.保存类的实例,即堆区对象的引用(指针)。3.用来保存加载方法时的帧,当嵌套方法调用时,嵌套越深,stack的内存就越晚才能释放,因此,在实际开发过程中,不推荐大家使用递归来进行方法的调用,递归很容易导致stack flow。

2.3 堆

每一个Java应用都唯一对应一个JVM实例,每一个实例唯一对应一个堆。应用程序在运行中所创建的所有类实例或数组都放在这个堆中。Java中所有对象的存储空间都是在堆中分配的,但是这个对象的引用却是在堆栈中分配,也就是说在建立一个对象时从两个地方都分配内存,在堆中分配的内存实际建立这个对象,而在堆栈中分配的内存只是一个指向这个堆对象的指针(引用)而已。

2.4 堆和栈的区别

2.5 方法区

JVM有一个被所有线程共享的方法区。方法区类似于传统语言的编译后代码的存储区,或者UNIX进程中的text段。它存储每个类结构例如常量池(constant pool),成员字段域和方法和构造函数,包含类和实例初始化和接口类型类型中用到的特殊方法的代码。

方法区在虚拟机启动时创建。尽管方法区在逻辑上是heap的一部分,简单的实现仍然可以选择对它既不回收也不压缩。

 

 

Byte  Character Boolean Short Integer Long实现了常量池技术,FloatDouble 没有实现常量池技术

 

·          Integer i1 = 40;  

·          Integer i2 = 40;

因为Integer实现了常量池技术,所以在池中i1i2指向同一个地址,故 i1 == i2 true

 

·          Double d1=1.0;  

·          Double d2=1.0; 

因为Double 没有实现常量池技术,所以Doubled1=1.0;相当于Double d1=new Double(1.0);

d2类同,各自new了一个对象,所以d1d2存放的指针不同,指向的对象不同,所以不相等

 

·  Integer i4 = new Integer(40);  

·  Integer i5 = new Integer(40); 

虽然Integer实现了常量池技术,但是他们各自new了一个对象。i4i5 均是引用类型,在栈中存储指针,因为Integer是包装类。但是由于他们各自都是new出来的,因此不再从常量池寻找数据,而是从堆中各自new一个对象,然后各自保存指向对象的指针,所以i4i5不相等,因为他们所存指针不同,所指向对象不同,故i4==i5为false。

 

但是需要注意的是:以上提到的几种基本类型包装类均实现了常量池技术,但他们维护的常量仅仅是【-128127】这个范围内的常量,如果常量值超过这个范围,就会从堆中创建对象,不再从常量池中取。比如,把上边例子改成Integer i1 = 400; Integer i2 = 400;,很明显超过了127,无法从常量池获取常量,就要从堆中new新的Integer对象,这时i1i2就不相等了。

 

对于i1==i2+i3i4==i5+i6结果为True,是因为,Java的数学计算是在内存栈里操作的,Java会对i5i6进行拆箱操作,其实比较的是基本类型(40=40+0),他们的值相同,因此结果为True

1
0

猜你在找
【直播】机器学习&数据挖掘7周实训--韦玮
【套餐】系统集成项目管理工程师顺利通关--徐朋
【直播】3小时掌握Docker最佳实战-徐西宁
【套餐】机器学习系列套餐(算法+实战)--唐宇迪
【直播】计算机视觉原理及实战--屈教授
【套餐】微信订阅号+服务号Java版 v2.0--翟东平
【直播】机器学习之矩阵--黄博士
【套餐】微信订阅号+服务号Java版 v2.0--翟东平
【直播】机器学习之凸优化--马博士
【套餐】Javascript 设计模式实战--曾亮
查看评论
* 以上用户言论只代表其个人观点,不代表CSDN网站的观点或立场
    个人资料
    • 访问:127763次
    • 积分:2069
    • 等级:
    • 排名:第18438名
    • 原创:86篇
    • 转载:31篇
    • 译文:0篇
    • 评论:11条
    文章分类
    最新评论