java的equals()方法

时间:2009-12-31 16:26:55

标签: java class

我有以下测试程序。我创建了3个Integer引用。我创建了2个Integer个对象,并使引用i1和i2分别引用它们。我使参考i3等于i1。现在i1 equals()i3显然应该是真的,因为它们都引用堆上的相同对象。但为什么i1应该与i2相等?他们引用了两个不同的对象。我错过了什么。

documentation说:

public boolean equals(Object obj)
     Indicates whether some other object is "equal to" this one.


public class Test{

    public static void main(String [] args)
    {
        Integer i1 = new Integer(10);
        Integer i2 = new Integer(10);
        Integer i3 = i1;

        if(i1.equals(i3)) // UNDERSTANDABLE
            System.out.println("equal");

        if(i1.equals(i2)) // prints equal. WHY !!!!!
            System.out.println("equal");    
}

}

10 个答案:

答案 0 :(得分:12)

包装类型的equals()方法测试值相等性,如果要测试引用相等性,请改用==,例如

System.out.println(new Integer(1) == new Integer(1));

答案 1 :(得分:5)

equals是相等的值版本。类重写此方法以定义值相等意味着什么。例如,要查看两个字符串是否包含相同的字符序列,请使用.equals()方法。如果要创建自己的类,并且例如要将其添加到HashMap,则必须同时定义hashCode()equals()方法才能使其正常工作。

要查看两个引用是否指向同一个内存位置,请使用==

答案 2 :(得分:4)

因为i1和i2具有相同的值。 Integer.equals()实现如下:

  public boolean equals(Object obj) {
    return (obj instanceof Integer 
            && intValue() == ((Integer) obj).intValue());
  }

所以i1和i2是整数,它们具有相同的值,因此它将返回true。

答案 3 :(得分:3)

Integer类的equals方法比较Integer包装的int值。当10等于10时,i1和i2被认为是相等的。

答案 4 :(得分:3)

通过查看Integer类,您可以更好地了解原因。以下是代码

/**
 * Compares this object to the specified object.  The result is
 * <code>true</code> if and only if the argument is not
 * <code>null</code> and is an <code>Integer</code> object that
 * contains the same <code>int</code> value as this object.
 *
 * @param   obj   the object to compare with.
 * @return  <code>true</code> if the objects are the same;
 *          <code>false</code> otherwise.
 */
public boolean equals(Object obj) {
if (obj instanceof Integer) {
    return value == ((Integer)obj).intValue();
}
return false;

答案 5 :(得分:2)

这是equals()Integer的实施:

public boolean equals(Object obj) {
if (obj instanceof Integer) {
    return value == ((Integer)obj).intValue();
}
return false;
}

考虑到这一点,如果i1的value为10,而i2的value也为10,则10 == 10将返回true。

答案 6 :(得分:2)

如果您在JavaDoc中进一步阅读,它会提供更多详细信息,特别是:

  

指示是否有其他对象   “等于”这个。等于   方法实现了等价   非空对象的关系   参考文献:

     
      
  • 它是自反的:对于任何非空引用值x,x.equals(x)应该是   返回true。
  •   
  • 它是对称的:对于任何非空参考值x和y,x.equals(y)   应该返回true,当且仅当   y.equals(x)返回true。
  •   
  • 它是传递性的:对于任何非空参考值x,y和z,if   x.equals(y)返回true和   y.equals(z)返回true,然后   x.equals(z)应该返回true。
  •   
  • 一致:对于任何非空引用值x和y,为多个   调用x.equals(y)   一贯回归真实或   如果没有,则一直返回虚假   用于等比较的信息   在对象上进行了修改。
  •   
  • 对于任何非空引用值x,x.equals(null)应返回false。
  •   

具体而言,由“equals(Object)”的实现者决定两个对象是否“相等”。为了参考比较,我们使用==运算符,正如其他人所指出的那样。

如果您对此(及其他类似)主题感兴趣,我也建议您阅读Effective Java

答案 7 :(得分:1)

你的问题的答案已经说过,但我有一个说明。要小心,因为你自己的对象是从Object扩展的,并且方法equal()像操作符==一样实现,所以如果你想比较值,你必须覆盖它。

答案 8 :(得分:1)

另请注意,“使用new Integer(int)保证始终生成新对象,而Integer.valueOf(int)允许由编译器,类库或JVM完成值的缓存。使用缓存值避免对象分配,代码会更快。“ - FindBugs

比较这些陈述:

System.out.println("new == " + (new Integer(1) == new Integer(1)));
System.out.println("new equals() " + new Integer(1).equals(new Integer(1)));
System.out.println("valueOf() == "
    + (Integer.valueOf(1) == Integer.valueOf(1)));
System.out.println("valueOf() equals() "
    + Integer.valueOf(1).equals(Integer.valueOf(1)));
产生此输出的

new == false
new equals() true
valueOf() == true
valueOf() equals() true

答案 9 :(得分:1)

它们具有相同的价值,这就是为什么它是真的。通常,equals方法不测试引用是否相等,尽管这是默认行为。