java不同类型之间的equal比较_==与equal的区别

一、java中的数据类型html

基本类型:如:int、short、long、float、double、boolean

引用类型

null类型:这是一个很是特殊的类型

二、基本类型之间的比较java

你们都知道基本之间的类型比较不能用equal,而是用==,那么用==是怎么比较大小的呢?咱们就来探一个究竟。面试

在计算机中,全部储存的东西都是用二进制来表示的,例如:01010101010101,那么基本类型在计算机中确定是用二进制表示的吧,可是数据储存是有必定格式的,不一样的类型数据的格式是不同的,下面介绍几种数据类型的储存格式。编程

boolean 类型

在java中,boolean是用一字节表示的,因为boolean 只有两个值,即0和1,用二进制表示就是为00000000和00000001oracle

int类型

在java中,int是用32位来储存的,并且是有符号的。下面就说一个例子:eclipse

好比说:100 在java中,表示为:00000000000000000000000001100100  而-100在java中,表示为:11111111111111111111111110011100函数

若是不知道把100和-100怎么转成这样二进制的话,那你就得先百度一下了,先学学这个知识了,由于我这里是总结==而不是进制之间的转换,在这里就细说了。spa

如今咱们已经把他们都转化为二进制了,这个时候能够开始比较了,在内存中,他们会一位一位地比较,很显然,他们不相等。整数之间的比较很是简单,接下来是float类型的比较了。orm

float类型

先明确float类型在计算机中是怎么被存储起来的,下面是介绍(下面这段介绍性文字是引用另一位高人的):htm

根据国际标准IEEE 754,任意一个二进制浮点数V能够表示成下面的形式:

V = (-1)^s×M×2^E

(1)(-1)^s表示符号位,当s=0,V为正数;当s=1,V为负数。

(2)M表示有效数字,大于等于1,小于2。

(3)2^E表示指数位。

举例来讲,十进制的5.0,写成二进制是101.0,至关于1.01×2^2。那么,按照上面V的格式,能够得出s=0,M=1.01,E=2。

十进制的-5.0,写成二进制是-101.0,至关于-1.01×2^2。那么,s=1,M=1.01,E=2。

IEEE 754规定,对于32位的浮点数,最高的1位是符号位s,接着的8位是指数E,剩下的23位为有效数字M。

 fa44ef8b960a44349500736e.html

对于64位的浮点数,最高的1位是符号位S,接着的11位是指数E,剩下的52位为有效数字M。

 fa44ef8b960a44349500736e.html

5.

IEEE 754对有效数字M和指数E,还有一些特别规定。

前面说过,1≤M<2,也就是说,M能够写成1.xxxxxx的形式,其中xxxxxx表示小数部分。IEEE 754规定,在计算机内部保存M时,默认这个数的第一位老是1,所以能够被舍去,只保存后面的xxxxxx部分。好比保存1.01的时候,只保存01,等到读取的时候,再把第一位的1加上去。这样作的目的,是节省1位有效数字。以32位浮点数为例,留给M只有23位,将第一位的1舍去之后,等于能够保存24位有效数字。

至于指数E,状况就比较复杂。

首先,E为一个无符号整数(unsigned int)。这意味着,若是E为8位,它的取值范围为0~255;若是E为11位,它的取值范围为0~2047。可是,咱们知道,科学计数法中的E是能够出现负数的,因此IEEE 754规定,E的真实值必须再减去一个中间数,对于8位的E,这个中间数是127;对于11位的E,这个中间数是1023。

好比,2^10的E是10,因此保存成32位浮点数时,必须保存成10+127=137,即10001001。

而后,指数E还能够再分红三种状况:

(1)E不全为0或不全为1。这时,浮点数就采用上面的规则表示,即指数E的计算值减去127(或1023),获得真实值,再将有效数字M前加上第一位的1。

(2)E全为0。这时,浮点数的指数E等于1-127(或者1-1023),有效数字M再也不加上第一位的1,而是还原为0.xxxxxx的小数。这样作是为了表示±0,以及接近于0的很小的数字。

(3)E全为1。这时,若是有效数字M全为0,表示±无穷大(正负取决于符号位s);若是有效数字M不全为0,表示这个数不是一个数(NaN)。

说完原理之后,接下来我就举一例子

1.00000000和1.000000001

按照上面的规则,1.00000000转化为V = (-1)^s×M×2^E这种形式:1.0*2^0,转化为二进制就是:0 01111111 00000000000000000000000

而1.000000001转化为V = (-1)^s×M×2^E这种形式:1.0*2^0,转化为二进制就是:0 01111111 00000000000000000000000

按照这种状况对比,能够得出1.00000000与1.000000001是相等的,对他们就是相等的。可是若是是64bit的时候就是否是相等的,这个你能够试一试。

double类型

double类型的比较跟float类型的比较实际上是同样的,只不过是把精度提升了,用的是64位,好比说:1.00000000和1.000000001的比较

1.00000000转化为二进制为0 01111111    0000000000000000000000000000000000000000000000000000

而1.000000001转化为二进制为0 01111111111 0000000000000000000000000000010001001011100000101111

很显然这两个数字是不相等的。

在float类型的比较,咱们会用Float.floatToIntbit(float value)这个函数来比较两个浮点数的大小,那么用Float.floatToInbit(float value)与用==来比较两个浮点数有什么不一样呢?Float.floatToInbit(float value)的原理是怎么样的呢?

先介绍Float.floatToInbit(float value)的原理:

官方文档是这样说的:Returns a representation of the specified floating-point value according to the IEEE 754 floating-point "single format" bit layout

举个例子来讲吧:

好比说:float a=1.00000000;  Float.floatToIntbit(a)=1065353216,这是怎么来的呢?原来是这样的,把1.00000000按照V = (-1)^s×M×2^E这个规则转成二进制就是:0 01111111 00000000000000000000000,接着把这个二进制转化为整数就是:1065353216了。

用Float.floatToIntbit(float value)跟用==来比较两个浮点数的大小有什么不一样呢?

对与通常的浮点数,用两种方法都同样。主要不一样的地方就是比较特殊的数,

NaN、-0.0 、 0.0

用==来比较就是 NaN==NaN是false     -0.0==0.0是true

用Float.floatToIntbit()来比较就是  Float.floatToIntbit(NaN)==Float.floatToIntbit(NaN)是true,而Float.floatToIntbit(0.0)==Float.floatToIntbit(-0.0)是false这个得解释一下,为何会出现这样的差异呢?

什么是NaN:她是指not a number,不是一个数,好比说1.0/0.0是多少呢,咱们定义这样的数为NaN。对于oo来讲,这就是咱们定义的一个对象,因此Float.floatToIntbit(NaN)==Float.floatToIntbit(NaN)就是true了,在这个函数里面NaN是对应一个整数的,查看jdk源码或者jdk文档就知道了。从数学的角度来讲:NaN==NaN是false,由于不是一个数怎么能跟不是一个数相等呢?0.0和-0.0的问题是比较好解析的,从数学的角度来讲-0.0与0.0是相等的,可是Float.floatToIntbit(-0.0)根据上面的规则就是2147483648  而Float.floatToIntbit(0.0)是0,因此很显然不相等。详情请看这里

那么咱们在编程中,通常用哪个来进行比较呢?是用==好呢?仍是用Float.floatToIntbit()这个好呢?这个就要看具体状况了,我如今也不知道用他们的通常规则

double之间的比较这里就不重复了,原理跟float同样。

三、对象之间的比较

咱们在作面试题目的时候常常会碰到下面这样的情形

String a="hello";

String b="hello";

String c=new String("hello");

System.out.println(a==b);//true

System.out.println(a==c);//false

System.out.println(a.equal(c))//true

为何会出现这样的结果呢?

分析:这三个引用指向的的对象的内容都是相同的,从逻辑上面来讲都是相等的。可是确实出现了上面的这种结果。那是由于==比的是对象的地址,对于同一个常量来讲,它的内存地址都是同样的,而c是指向新开除来内存,因此a==c是false,而a.equal(b)比的是对象的内容,与对象所在的地址无关,因此a.equal(c)是true。

四、null类型之间的比较,

能够按照eclipse里面自动生成的equal函数的比较方式。任何其余类型跟null比较都是不等的,null。equal(null)是无心义的。

总结:

一、基本类型之间的比较通常是用==,可是注意float和double类型的精度问题以及NaN、正无穷大、负无穷大、-0.0、0.0的比较问题

二、引用类型的比较通常是用equal,尤为是字符串,由于==是指对象地址之间的比较,而对象地址之间的比较通常是无心义的。

  • 0
    点赞
  • 0
    收藏
    觉得还不错? 一键收藏
  • 0
    评论

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

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

余额充值