java中的equals与==的比较

原创 2016年08月28日 16:37:21
equals 方法是 java.lang.Object 类的方法。

有两种用法说明:

(1)对于字符串变量来说,使用“==”和“equals()”方法比较字符串时,其比较方法不同。

“==”比较两个变量本身的值,即两个对象在内存中的首地址。

“equals()”比较字符串中所包含的内容是否相同。

比如:

String s1,s2,s3 = "abc", s4 ="abc" ;
s1 = new String("abc");
s2 = new String("abc");

 那么:

s1==s2   是 false      //两个变量的内存地址不一样,也就是说它们指向的对象不 一样,故不相等。
s1.equals(s2) 是 true    //两个变量的所包含的内容是abc,故相等。

注意(1):

StringBuffer s1 = new StringBuffer("a");
StringBuffer s2 = new StringBuffer("a");             
s1.equals(s2)  //是false

解释:StringBuffer类中没有重新定义equals这个方法,因此这个方法就来自Object类,而Object类中的equals方法是用来比较“地址”的,所以等于false.

注意(2):

对于s3和s4来说,有一点不一样要引起注意,由于s3和s4是两个字符常量所生成的变量,其中所存放的内存地址是相等的,所以s3==s4是true(即使没有s3=s4这样一个赋值语句)


(2)对于非字符串变量来说,"=="和"equals"方法的作用是相同的都是用来比较其
对象在堆内存的首地址,即用来比较两个引用变量是否指向同一个对象。

比如:

class A
{
      A obj1   =   new  A();
      A obj2   =   new  A();
}
obj1==obj2是false
obj1.equals(obj2)是false

但是如果加上一句:

obj1=obj2;
那么 :
obj1==obj2  是true
obj1.equals(obj2) 是true

总之:equals方法对于字符串来说是比较内容的,而对于非字符串来说是比较其指向的对象是否相同的。

         == 比较符也是比较指向的对象是否相同的也就是对象在对内存中的的首地址。

String类中重新定义了equals这个方法,而且比较的是值,而不是地址。所以是true。

关于equals与==的区别从以下几个方面来说: 

(1) 如果是基本类型比较,那么只能用==来比较,不能用equals 

比如: 
public class TestEquals { 
  public static void main(String[] args) 
  { 
    int a = 3; 
    int b = 4; 
    int c = 3; 
    System.out.println(a == b);//结果是false 
    System.out.println(a == c);//结果是true 
    System.out.println(a.equals(c));//错误,编译不能通过,equals方法 
    //不能运用与基本类型的比较 
  } 
}

(2) 对于基本类型的包装类型,比如Boolean、Character、Byte、Shot、Integer、Long、Float、Double等的引用变量,==是比较地址的,而equals是比较内容的。比如: 
public class TestEquals { 
  public static void main(String[] args) 
  {
    Integer n1 = new Integer(30); 
    Integer n2 = new Integer(30); 
    Integer n3 = new Integer(31); 
    System.out.println(n1 == n2);//结果是false 两个不同的Integer对象,故其地址不同, 
    System.out.println(n1 == n3);//那么不管是new Integer(30)还是new Integer(31) 结果都显示false 
    System.out.println(n1.equals(n2));
    //结果是true 根据jdk文档中的说明,n1与n2指向的对象中的内容是相等的,都是30,故equals比较后结果是true 
    System.out.println(n1.equals(n3));//结果是false 因对象内容不一样,一个是30一个是31 
  } 
}


这是Integer的实例,如果是其他的比如Double、Character、Float等也一样。

(3) 注意:对于String(字符串)、StringBuffer(线程安全的可变字符序列)、StringBuilder(可变字符序列)这三个类作进一步的说明。 
(a)首先,介绍String的用法,请看下面的实例: 
public class TestEquals { 
  public static void main(String[] args) { 
    String s1 = "123"; 
    String s2 = "123"; 
    String s3 = "abc"; 
    String s4 = new String("123"); 
    String s5 = new String("123"); 
    String s6 = new String("abc"); 

    System.out.println(s1 == s2);//(1)true 
    System.out.println(s1.equals(s2));//(2)true 
    System.out.println(s1 == s3);//(3)flase 
    System.out.println(s1.equals(s3));//(4)flase 

    System.out.println(s4 == s5);//(5)flase 
    System.out.println(s4.equals(s5));//(6)true 
    System.out.println(s4 == s6);//(7)flase 
    System.out.println(s4.equals(s6));//(8)flase 

    System.out.println(s1 == s4);//(9)false 
    System.out.println(s1.equals(s4));//(10)true 
  } 
} 
答案解释:s1与s2分别指向由字符串常量”123” 创建的对象,在常量池中,只有一个对象,内容为123,有两个引用s1和s2指向这个对象,故这两个引用变量所指向的地址是相同的,因而(1)处的运行结果为true,又因为s1.equals(s2)是比较s1和s2所指向的对象的内容是否相等,而我们知道这两个对象的内容都是字符串常量”123”,故标记(2)处的运行结果是true。
 
用同样的方法分析,s1和s3所指向的对象不一样,内容也不一样,故标记(3)和(4)处运行结果是false。 

再看看s4和s5,这两个引用变量所指向的对象的内容都是一样的(内容都是123),但是这两个对象是用new操作符创建处类的,是在内存中分配两块空间给这两个对象的,因而这两个对象的内存地址不一样,故事两个不同的对象,标记(5)处的s4 == s5 运行结果为false,但是内容一样,故标记(6)处的s4.equals(s5)运行结果为true。同理,s4和s6所指向的对象地址不同,内容也不相同。故标记(7)(8)处运行结果为false。 

s1和s4分别指向两个不同的对象(之所以这样称呼,是因为这两个对象在内存中的地址不相同,故而对象不相同),故标记为(9)处的s1 == s4运行结果为false,而标记为(10)处的s1.equals(s4)运行结果为true.

(4) 再看一种情况,先看一个例子(该例子是Java编程思想第三章的例子): 
class Value 
{ 
  int i; 
} 
public class EqualsMethod2 { 
  public static void main(String[] args) { 
    Value v1 = new Value(); 
    Value v2 = new Value(); 
    v1.i = v2.i = 100; 
    System.out.println(v1.equals(v2));//(1)flase 
    System.out.println(v1 == v2);//(2)true 
  } 
} 
运行结果疑问:乍一看结果,有点惊讶,为什么不是true呢,不是说equals方法是比较内容的吗? 

解释:不错,如果在新类中被覆盖了equals方法,就可以用来比较内容的。但是在上面的例子中类Value并没有覆盖Object中的equals方法,而是继承了该方法,因此它就是被用来比较地址的,又v1和v2的所指向的对象不相同,故标记(1)处的v1.equals(v2)运行结果为false,标记为(2)处的v1 == v2运行结果也为false。 
版权声明:本文为博主原创文章,未经博主允许不得转载。

Java中两个对象的比较 equals()方法和==号的区别

在Java中,时不时我们会把两个对象进行,然而得到的结果却不是我们想的结果,这是怎么回事呢? 一、两种形式的比较:比较时,我们要弄清楚是哪一种比较。       1.值类型比较       即内容...
  • BlueSky_USC
  • BlueSky_USC
  • 2016年07月07日 10:28
  • 10666

Java中==、equals()和hashCode()的比较分析

在Java语言中,==、equals()、hashCode()这三个方法都和对象的比较有关,
  • taohuaxinmu123
  • taohuaxinmu123
  • 2014年06月17日 10:10
  • 2322

Java 语言的几个缺陷之二: equals() 比较字符串

转载自:http://unmi.cc/java-language-defect-2-equals-compare-strings/ 对于面向对象的语言不知道除了 Java 还有没别的语言会拿怎么...
  • gzq110103
  • gzq110103
  • 2016年08月04日 22:55
  • 1696

什么时候应该用equals(),什么时候应该用==

本人小白一枚最近这一部分比较晕,所以自己就仔细研究了一下 我结合网上和自己的理解总结了一些,如果我说的有问题,也请大家及时提醒,不足或漏说的地方愿大家积极 补充以供更多小白得到帮助,在此谢谢大家了! ...
  • fox_bert
  • fox_bert
  • 2016年02月12日 13:37
  • 1257

String比较为什么要用equals?用==的问题

很简单的问题,记录一下 下面的程序很简单吧?你能保证你说的结论都是正确的吗?运行验证下你的猜测。 public class T{ public static void main(String[] a...
  • look_dev
  • look_dev
  • 2016年10月22日 17:31
  • 555

java中equals和等号(==)的区别浅谈

java中的数据类型,可分为两类: 1.基本数据类型,也称原始数据类型。 byte,short,char,int,long,float,double,boolean   他们之间的比较,应用双等号...
  • qq_32907417
  • qq_32907417
  • 2016年02月16日 10:11
  • 4720

java-equals和==的比较规则和equals的重写

1、java中equals和==的区别 值类型是存储在内存中的堆栈(简称栈),而引用类型的变量在栈中仅仅是存储引用类型变量的地址,而其本身则存储在堆中。 2、==操作比较的是两个变量的值是否相等,对...
  • defineshan
  • defineshan
  • 2016年08月22日 15:12
  • 745

从Java的堆栈到Equals和==的比较

认识Java中堆和栈 栈与堆都是Java用来在Ram中存放数据的地方。与C++不同,Java自动管理栈和堆,程序员不能直接地设置栈或堆。 Java的堆是一个运行时数据区,类的对象从中分配空...
  • u012959829
  • u012959829
  • 2015年03月20日 00:03
  • 895

java中 “==”和“equals”以及instanceof的区别

java基础之 “==”和“ equals”以及instanceof的区别 (1)对于字符串变量来说,使用“==”和“equals()”方法比较字符串时,其比较方法不同。 “==”比较两个...
  • shenxiuwen1989
  • shenxiuwen1989
  • 2014年05月25日 09:23
  • 700

对象的比较及hashCode、equals方法的使用

如何进行对象的值的比较呢?如String类型的变量,是靠调用equals方法来比较的,而其它的类似数组或普通的对象直接调用equals方法一般是不可以的,这是因为String类型的变量通过调用equa...
  • dfb198998
  • dfb198998
  • 2015年08月18日 09:47
  • 1065
内容举报
返回顶部
收藏助手
不良信息举报
您举报文章:java中的equals与==的比较
举报原因:
原因补充:

(最多只允许输入30个字)