equals,== 数据比较详细分析

关于数据equals和== 的区别:
本质区别:equals 比较的是值的hashcode;
而 == 比较的值的内存地址是否一样。

以下以String 为例:
根据String 源码中方法intern()返回值为String;英文释义:拘留,软禁。
顾名思义:从软禁区域获取一个String 并返回。软禁区域则为 常量池。

非new的情况:
String a = “abc”;
String b = “abc”;
a == b ;//结果:true
释义:a 对象形成的时候,会在常量池中找有没有“abc”的字符串;如果没有,形成一个“abc”字符串在常量池。并在栈中将句柄(引用)指向常量池。b同理,则指向的为同一个,abc的地址则为同一个地址。所以为true。
new的情况:
String a = new String(“abc”);
String b = new String(“abc”);
a == b ;//结果: false
释义: a对象形成的时候,会先去常量池中找有没有“abc”的字符串,若没有,则在常量池中创建一个abc的对象,并拷贝一份,放在堆中。将栈中句柄a指向堆中地址(假设地址别名为:上海)。b则同a一样操作,只不过,a形成的时候已经在常量池中产生了“abc”,b则直接拷贝一份,放在堆中,并将栈中句柄b指向堆中地址(假设地址别名为:北京)则北京和上海地址不一致。(个人见解缘由:每次去常量池中的判断,为了提高性能,提高效率,节约开销。)
总结:非new的情况下,会指向常量池中,new的情况下会指向堆中。

进阶一步:
String a = “kfc”;//常量池中地址假设:南京
String b = “mds”;//常量池中地址假设:苏州
String c = a+b;//c的地址为堆中地址假设:江苏
前方高能:c = new StringBuilder().append(a).append(b).toString();
注意:StringBuilder类中的toString()源码返回值为:new String(xxx);c在运行时实际上形成的是一个新的字符串新的地址。
c == (a+b);//显然为false;

String d = "nbacba";//假设常量池中地址为:无锡
String e = "nba"+"cba";//e的字面还是nbacba;显然地址为无锡。

d == e;//结果true;

再进一步:
public Test{
public static final a = “kfc”;
public static final b = “mds”;
String c = a+b;//注意:a,b在编译阶段已经形成了常量;所以c = “kfc”+”mds”;//同样为常量池中的地址,假设为:上海
String d = “kfc”+”mds”; //常量池的地址同样为上海。
c == d ;//结果:true
}

接下来开始解析String 源码方法intern:
String a = new String(“abc”);//地址为堆中(假设地址别名:上海),常量池中“abc”地址假设为深圳。
String b = a.intern();//根据文章开头所示:b 则指向的是深圳。
String c = “abc”;//c 是从常量池中直接获取,则指向深圳。
a == b ;//结果false
b == c;//结果true
所有数据类型总结:

1.基本数据类型 byte short int long char float double boolean;
== 比较的是 值是否相等。
注意:没有实现常量池的Float和Double。
如栗子:
Double a = 1.0;
Double b = 1.0;
a == b; //false


2.引用数据类型:自定义的对象,数组等等。
一般情况下,equals和==是一样的都是比较的两者的地址值是不是一样。
但是有特殊的情况:我们都知道我们使用的类都是继承自Object基类,
Object中equals方法中是使用==来实现的,即比较的是两者的地址值。
比如Date、String、Integer等类都是重写了equals都是重写了,比较的是值是否相等。

关于未重写的equals比较都均为hashCode值。

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

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

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

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值