2

让我们看看我们有 2 个对用户定义类实例的引用,Java 中的 a 和 b。是否会出现 a == b 但 a.equals(b) 返回 false 的情况?

4

8 回答 8

8

当然!的实现.equals()完全取决于班级,所以我可以写:

class Foo
    public boolean equals(Object other) {
        return false;
    }
}

现在,你通过什么两个实例并不重要——即使是完全相同的实例两次——我总是会说它们不相等。

这种特别的设置很愚蠢,但它说明您可以false.equals()同一对象获得两次结果。

请注意,我们在这里谈论的是可能发生的事情,而不是应该发生的事情。任何类都不应该实现.equals声称对象不等于自身的方法。对于受信任的代码,可以合理地假设这永远不会发生。

于 2012-07-07T20:17:49.093 回答
4

是的,只是超载equals做一些愚蠢的事情。例如

class Foo {
    @Override
    boolean equals(Object rhs) { return false; }
}
于 2012-07-07T20:17:39.103 回答
3

if a == b那么a.equals(b)应该是真的。如果a.equals(b)那么可能a == b但不一定。

操作员只是测试两者==是否引用同一个对象。Whileequals执行您实现的逻辑。最后一个可以被覆盖第一个是语言中的运算符,例如在 Java 中不能被覆盖。

参考

== 运算符和 equals() 有什么区别?(使用哈希码()???)

java.lang.Object文档:

equals 方法在非空对象引用上实现等价关系:

  1. 它是自反的:对于任何非空引用值 x,x.equals(x) 应该返回 true。
  2. 它是对称的:对于任何非空引用值 x 和 y,当且仅当 y.equals(x) 返回 true 时,x.equals(y) 才应该返回 true。
  3. 它是可传递的:对于任何非空引用值 x、y 和 z,如果 x.equals(y) 返回 true 并且 y.equals(z) 返回 true,则 x.equals(z) 应该返回 true。
  4. 它是一致的:对于任何非空引用值 x 和 y,x.equals(y) 的多次调用始终返回 true 或始终返回 false,前提是没有修改对象上 equals 比较中使用的信息。
  5. 对于任何非空引用值 x,x.equals(null) 应该返回 false。
于 2012-07-07T20:24:14.590 回答
2

正如其他答案所指出的那样,显然可以编写执行此操作的代码。

但是,它也始终是代码中的逻辑错误,因为它违反了 equals() 函数的隐式通用合同。

一个对象应该总是等于它自己,所以 if (a==b)thena.equals(b) 应该总是返回 true。

于 2012-07-07T20:44:03.050 回答
1

是的,我们可以重载该.equals函数以提供所需的输出。但是没有任何情况下==返回真而.equals返回假。

class s {
    int a;
}

class dev {
    public static void main(String args[]) {
        s a = new s();
        s b = new s();
        System.out.println(a == b);
        System.out.println(a.equals(b));
    }
}
输出
错误的
错误的
于 2012-07-07T20:29:52.213 回答
0

是的,很容易:

public class Wrong{
    public boolean equals(Object other) 
    {
    return false;
    }
}

当然,这完全违反了实现的正常规则.equals()- 请参阅Javadocs - 但除了明智之外,没有什么可以阻止您。

于 2012-07-07T20:17:57.043 回答
0

可以重写该equals方法以提供不同于典型==方法的自定义功能。此外,某些类型,例如Strings在使用 == 方法时不会返回 true。您必须使用.equals.compareTo(当返回 0 时等于)。

这应该提供一些额外的帮助

于 2012-07-07T20:18:49.577 回答
0
package com.stackOverFlow;

import java.util.Date;

public class SampleClass {

public static int  myint = 1;
private SampleClass() {
};

public Integer returnRandom() {
    return myint++;
}

private static SampleClass _sampleClass;

public static SampleClass getInstance() {

    if (_sampleClass == null) {
        _sampleClass = new SampleClass();
    }
    return _sampleClass;
}

@Override
public boolean equals(Object other) {
    if (this.returnRandom().equals(((SampleClass) other).returnRandom())) {
        return true;

    }
    return false;
}

}



package com.stackOverFlow;

public class Run {

/**
 * @param args
 */
public static void main(String[] args) {
    // TODO Auto-generated method stub

    SampleClass a = SampleClass.getInstance();
    SampleClass b = SampleClass.getInstance();
    if(a==b){
        System.out.println("references are same as they are pointing to same object");
        if(!a.equals(b)){
            System.out.println("two random number Instance will never be same");
        }
    }

}

}

您可以通过实际示例来理解这一点。其中单例类将始终返回相同的引用,并且您可以覆盖 equals 方法以获取不是类变量的内容。例如在两个特定时间来自数据库的值,或随机数。希望可以清除您的情况

于 2012-07-07T20:49:12.883 回答