ICode9

精准搜索请尝试: 精确搜索
首页 > 编程语言> 文章详细

Java-整数类型常量池

2021-05-26 23:05:14  阅读:181  来源: 互联网

标签:Java 常量 i1 System 整数 hashCode println Integer out


使用整数的封装类型Byte、Short、Integer、Long定义变量时,经常会遇到Integer i1=1;和Integer i2=new Integer(1);判断i1==i2的情况,但是对于Short s1=1;s1和i1比较如何呢?

理论上占用的字节都不一样,应该不是同一个常量池,但是还有自动转型这个东西,会不会是short转成了所以对此有了怀疑。

1.整数类型常量池

整数类型的封装类型Byte、Short、Integer、Long会将一些常用的数放进常量池,提高性能;没有用new声明变量的情况下,默认引用堆内存上的常量池,这个范围为[-128,127],同种类型的几种声明方式及其变量指向的地址如下图所示:

拆箱,任何比较中有基本数据类型例如i2,全部自动拆箱比较数值,i1至i6与i2比较都返回true;

2.利用hashCode()判断是不是同一个对象

hashCode()就是根据一定的规则将与对象相关的信息(比如对象的存储地址,对象的字段等)映射成一个数值,这个数值称作为散列值。对象在jvm上的内存位置是唯一的,但是不同对象的hashcode可能相同,它还要包括其他内容,再根据一定的算法去算出一个值,算出来的可能一样,一样的话就是哈希冲突。

我认为哈希冲突的概率极低,虽然不同的对象算出的哈希值可能相同,写几个简单的用例不可能会遇到;

相同的对象hashCode()相同,返过来,hashCode()相同的对象地址一般都相同;

(1)声明测试类class Node{int x,y;}并测试

        Node node1=new Node();
        Node node2=new Node();
        Node node3=node1;
        System.out.println(node1.hashCode());//1163157884
        System.out.println(node2.hashCode());//1956725890
        System.out.println(node3.hashCode());//1163157884
        System.out.println(node1==node2);//false
        System.out.println(node1==node3);//true

普通类调用hashCode()是个native方法,返回一个哈希值,显然哈希值相同就是同一个对象;

(2)测试Integer 和 Short类型

        Short s1=1;
        Short s2=1;
        Integer i1=1;
//Integer i2=s2;//报错 System.out.println(s1==s2);//true //显示异常:Operator '==' cannot be applied to 'java.lang.Short', 'java.lang.Integer' //System.out.println(s1==i1); System.out.println(s1.hashCode());// 1 System.out.println(i1.hashCode());// 1

封装类型不能自动转型;

基本数据类型调用的hashCode()则是返回数值大小,这.....怎么判断是不是同一个对象?

==也不能用来判断,这......还怎么判断?

向同学请教怎么搞到s1和i1的地址,总算知道了

3.jol-core依赖包

openjdk的一个工具,可以查看到一个对象的布局。

        <dependency>
            <groupId>org.openjdk.jol</groupId>
            <artifactId>jol-core</artifactId>
            <version>0.9</version>
        </dependency>
        System.out.println(GraphLayout.parseInstance(i1).toPrintable());
        System.out.println("Current address: " + VM.current().addressOf(i1));
        System.out.println("------------------------------------------------------------------");
        System.out.println(GraphLayout.parseInstance(s1).toPrintable());
        System.out.println("Current address: " + VM.current().addressOf(s1));

终于可以盖棺定论,不同整数的封装类型数值为[-128,127]时使用的不是同一个常量池。

 

标签:Java,常量,i1,System,整数,hashCode,println,Integer,out
来源: https://www.cnblogs.com/shoulinniao/p/13802404.html

本站声明: 1. iCode9 技术分享网(下文简称本站)提供的所有内容,仅供技术学习、探讨和分享;
2. 关于本站的所有留言、评论、转载及引用,纯属内容发起人的个人观点,与本站观点和立场无关;
3. 关于本站的所有言论和文字,纯属内容发起人的个人观点,与本站观点和立场无关;
4. 本站文章均是网友提供,不完全保证技术分享内容的完整性、准确性、时效性、风险性和版权归属;如您发现该文章侵犯了您的权益,可联系我们第一时间进行删除;
5. 本站为非盈利性的个人网站,所有内容不会用来进行牟利,也不会利用任何形式的广告来间接获益,纯粹是为了广大技术爱好者提供技术内容和技术思想的分享性交流网站。

专注分享技术,共同学习,共同进步。侵权联系[81616952@qq.com]

Copyright (C)ICode9.com, All Rights Reserved.

ICode9版权所有