【问题标题】:java How To override the hashcode() and equals() of a specific arrayList itemjava如何覆盖特定arrayList项的hashcode()和equals()
【发布时间】:2018-05-10 15:38:41
【问题描述】:

好的,所以我的问题很简单。我搜索了 StackOverFlow、google 和 JavaDocs 高低,但似乎找不到我的具体问题的答案。

据我了解(这里归结为基础知识),每个对象都有一个 hashCode() 作为唯一标识符。我们将以此为例...

class Team {
        public Team(String teamName){teamName.this = teamName;}
        String teamName;
    }

    class NBALeague {
        ArrayList<Team> teamsInALeague = new ArrayList<>();
        teamsInALeague.add(new Team("Rockets"));
        teamsInALeague.add(new Team("Warriors"));
        teamsInALeague.add(new Team("Cavaliers"));
        teamsInALeague.add(new Team("76ers"));
    //each unique team when instantiated is assigned a hashCode!

        //now when I change the objects (or add to them rather) they are then 
        //each given a new hashCode()

          public void buildASchedule(){
             Team rockets = teamsInALeague.get(0);
             Team warriors= teamsInALeague.get(1);
             Team cavaliers= teamsInALeague.get(2);
             Team philly= teamsInALeague.get(3);

             String definingString = "This Team is Called: ";

             ArrayList anotherArrayList = new ArrayList();

             anotherArrayList.add(definingString + rockets.teamName);
             //Moving an object from one array list to another doesnt affect
             //its hashcode(), but adding a string to the object does

既然anotherArrayList.get(0) 有了一个全新的哈希码,我该如何覆盖它?

我知道我必须重写 hashcode()equals() 方法,以确保在放入 HashSet 时,该集合可以识别重复项,但是因为这些新的哈希码是在向对象添加字符串时生成的我不知道如何覆盖哈希码。通常我会通过 Team 类覆盖这两种方法,但同样不会因为更改对象创建新的哈希码而起作用。请有人帮忙!!!

【问题讨论】:

  • 你通过扩展类来覆盖方法
  • 好吧,即使我扩展了类,我也无法使用 override 方法来定位特定的连接项......如果你能给我看一个很棒的例子!非常感谢!
  • 哈希码的默认实现会为同一个对象返回相同的哈希值。如果 ojbect 有一个 String 字段并且您填充了该字段,则哈希仍然是相同的。如果您看到它发生了变化,那是因为它正在创建一个不同的对象。
  • "每个对象都有一个 hashCode() 作为唯一标识符" 不。它不是唯一的 ID。它是一个整数,所以大约有 50 亿种可能性,但 you don't actually need very many objects to be fairly certain of a collision
  • 嗯......很好的解释......好吧,也许我的例子对于我的实际问题来说过于简化了。让我们假设“teamName”字段不存在。如果一个对象连接到另一个对象以形成一个 arrayList 项(例如,如果我采用:anotherArrayList.add(rockets + Warriors); 并创建一个新的 hashcode(),我将如何覆盖这个新的具体的哈希码?

标签: java overriding equals hashset hashcode


【解决方案1】:

您似乎有两个误解:hashCode 究竟是什么,以及 + 运算符的工作原理。

我将首先解决后者。除了赋值 (=) 之外,当您在对象上应用运算符时,它不会以任何方式更改对象。声明

anotherArrayList.add(definingString + rockets.teamName);

不会以任何方式更改或影响rockets 变量。它不会“更改 hashCode”或任何其他关于它的东西,它只是复制 rockets.teamName 的值,将它与其他东西连接起来,然后创建一个全新的对象。而且那个全新的对象将是一个字符串,所以无论如何你都不能将它添加到列表中。

现在,关于 hashCode。对象没有“分配哈希码”或类似的东西。 hashCode() 没有什么特别的、神奇的或自动的,它只是一个返回整数的方法。它返回你告诉它返回的内容,如果你不覆盖它,默认实现会返回一个从不为给定对象更改的数字。

如果您将对象替换另一个对象,例如将另一个Team 放在列表中的该位置,那么该对象将拥有自己的hashCode,可能与第一个不同。但只需使用对象或其字段之一 不会以任何方式影响它。

【讨论】:

  • 新编辑:ArrayList anotherArrayList = new ArrayList(); anotherArrayList.add(definingString + rockets.teamName);如前所述,这不会改变原始值。但它确实创建了一个新对象,它是一个组合字符串现在假设我想将这个新字符串放入一个哈希集中,并且我想确保没有 2 个字符串出现两次我意识到我必须覆盖 hashcode() 和 equals () 方法,但由于这些是不是 Team 对象的新字符串,我会在 NBA Leagues 类中覆盖这些方法吗?如果是这样,有人可以举个例子吗
猜你喜欢
  • 1970-01-01
  • 1970-01-01
  • 2020-06-09
  • 1970-01-01
  • 2011-04-24
  • 1970-01-01
  • 2017-11-19
  • 1970-01-01
  • 1970-01-01
相关资源
最近更新 更多