【问题标题】:When to include what?什么时候包括什么?
【发布时间】:2012-06-06 11:01:36
【问题描述】:

我创建了一个类Person(正如书中所说)来保存从键盘输入的人的姓名和姓氏,然后还有另一个类PhoneNumber,它封装了国家代码、区号和号码一个人的字符串。
Person 旨在用作 Hashmap 中的键。
BookEntry 类封装了PersonPhoneNumber。很多BookEntry 对象组成了一个代表电话簿的HashMap。

Person 实现了Comparable<Person>,因此它包含CompareTo(Person) 方法。后来本书添加了equals(Object anotherPerson)method。
我的问题是,CompareTo 方法不足以比较两个键吗?还是 HashMap 的内部机制要求我包含 equals() 方法来比较两个键?
compareTo()

public int compareTo(Person person) {
    int result = lastName.compareTo(person.lastName);
    return result==0? firstName.compareTo(person.firstName):result;
}

equals()

public boolean equals(Object anotherPerson){
    return compareTo((Person)person)==0;
}

【问题讨论】:

  • equals() 的参数不一定是 Person 或其子类。
  • 您的equals() 实施不完整。您必须检查参数对象是否实际上是Person 类型。
  • 我知道。如果我通过 String ,程序崩溃:)

标签: java hashmap comparable compareto


【解决方案1】:

有些数据结构会使用compareTo(例如TreeMap),有些会使用equals(例如HashMap)。

更重要的是,强烈建议compareToequals保持一致,如Comparator javadoc中所述:

强烈建议但不严格要求 (x.compareTo(y)==0) == (x.equals(y))。一般来说,任何实现了 Comparable 接口并违反此条件的类都应该清楚地表明这一事实。推荐的语言是“注意:这个类有一个与equals不一致的自然顺序。”

另一个提示,在TreeMap javadoc(强调我的)中找到:

请注意,与任何排序图一样,由树状图维护的排序,以及是否提供显式比较器,如果该排序图要正确实现 Map 接口,则必须与 equals 保持一致.

最后,如果您覆盖equals,您还应该覆盖hashcode,以防止在使用基于散列的结构时出现意外行为。

【讨论】:

  • 所以如果我不知道哪个数据结构使用什么,我可以使用两者的组合,就像我的情况一样:)
  • @FasihKhatib 是的,如果你的类实现了Comparable,最好在compareTo 实现中一致地覆盖equalshashcode。它将在以后为您节省头部抓挠的错误。但是如果这是您的问题,您的类 不需要实现 Comparable 以在 HashMap 中使用。
【解决方案2】:

compareTo()方法用于排序,

此方法的实现将确定两个人之间谁更大(更小,相同),以及在什么程度上

equals()hashcode() 在您的情况下将用于基于哈希的数据结构 (HashMap)

用户自定义类作为HashMap的key

是的,您需要正确实施 hashcode()equals()

另见

【讨论】:

  • 所以基本上,如果我使用用户定义的类作为键,那么它必须有一个equals() 和一个compareTo() 方法供内部机制使用,如果我理解正确的话:)
  • user-defined class as a key of HashMap 是的,你需要正确实现 hashcode()equals()
  • 你不一定有一个 equals() 方法。默认情况下,equals 只使用 == 来表示相等,这适用于很多情况。
  • @Polygnome 不是真的看:stackoverflow.com/questions/5581913/…
【解决方案3】:

HashMap 使用equals() 而不是compareTo(),所以你必须实现它。 TreeMap 使用 compareTo()

【讨论】:

  • 但要让equals() 工作,我需要compareTo()。现在有意义了:)
  • 不,对于HashMap,您不一定需要compareTo()。您需要 equalshashCode 保持一致。就是这样。
  • compareTo() 中编写代码并从equals() 中调用它,或者直接在equals(). What is important is that your equals() 中编写代码应该可以正常工作。
猜你喜欢
  • 2020-01-09
相关资源
最近更新 更多