12

我有一个关于equals在 Java 中覆盖方法的问题。在我的书中,我有以下示例:

public class Dog{
     private String name;
     private int age;

public boolean equals(Object obj) {
    if(!(obj instanceof Dog)) return false;
    Dog other = (Dog) obj;                    ---> confused here
    if(this.name.equals(other.name) && (this.age == other.age) {
     return true;
    }
    else {
     return false;
    }
  }
}

我不明白为什么必须将引用转换为Dog引用。如果该引用不是类型Dog,我们将返回 false。为什么铸造它的所有麻烦?

4

7 回答 7

8

声明的类型objObject,所以你必须强制转换它来告诉编译器它是一个Dog.

尽管在逻辑上它不能是代码中的其他任何东西,但编译器对逻辑一无所知——它只知道类型。

于 2013-05-11T13:22:14.097 回答
6

因为您正在为相等定义自己的参数,所以您必须确保它们是同一个类。也就是说,除非您以这种==方式比较它们,否则您需要比较对象内部的一些值。要比较对象内部的值,它们需要是相同的类型!

例如,假设您有两个Dogs。

Dog dog1 = new Dog("Fido");
Dog dog2 = new Dog("Rover");

如果您想测试它们是否具有相同的名称,我相信您知道,您不能使用:

if(dog1 == dog2)

所以你覆盖了equals方法。但是,因为您要覆盖它,所以它必须具有相同的方法签名。方法签名由方法的名称、参数的数量和类型定义。这意味着如果你想覆盖它,它需要有一个 type 的参数Object。因此:

if(dog1.equals(dog2))

您需要将其转换为使用您使用的任何方法name从狗那里获取值并比较这些值的原因。

关于课堂设计的注释

面向对象编程中的约定,当然在 Java 中,是拥有AccessorMutator方法来获取和更改类中的变量。那是:

dog1.name; ----> dog1.getName();

getName()看起来像:

public String getName()
{
    return name;
}
于 2013-05-11T13:14:34.603 回答
0

对于 JVM,obj 是 Dog 并不那么明显,因此您必须明确使用强制转换。

于 2013-05-11T13:16:32.187 回答
0

因为作为方法参数objObject类的实例。所以在方法体中你需要转换objDog类型。

于 2013-05-11T13:18:12.843 回答
0

您正在覆盖 equals 方法以通过value not by reference..检查相等性

即,如果它们相同 ,则您希望两只狗相等,如果它们由同一个人所有,则不相等(即,如果它们的引用相同nameage 则不相等)


没有演员表,您无法访问狗nameage成员

于 2013-05-11T13:16:07.920 回答
0

属性nameage仅特定于Dog。您无法访问nameage使用obj,这是一个Object. 例如,以下代码将生成编译时错误

this.name.equals(obj.name)

我不明白为什么必须将引用转换为 Dog 引用。如果该引用不是 Dog 类型,我们将返回 false。为什么铸造它的所有麻烦?

因为虽然引用是Dog它并不意味着它是同一只狗。另一只狗的名字可能和你的不一样Dog。为了将nameandage的 otherDog与 your进行比较Dog,必须先进行转换。

于 2013-05-11T13:23:05.773 回答
0

我认为您的演示类缺少 hashCode() 方法。只有当它们对覆盖的 hashCode() 的调用相等时,这两个对象才能相等。(相同的整数值)。

我很确定你需要两者来保证这个等式。

于 2016-04-04T23:36:09.937 回答