我似乎无法得到HashSet实例按预期运行。我使用的代码如下所示:

import testing.Subclass;
import java.util.HashSet;

public class tester {
  public static void main(String[] args) throws Exception {
    HashSet<Subclass> set = new HashSet<Subclass>();
    set.add(new Subclass("007812"));
    set.add(new Subclass("007813"));
    System.out.println("Set size " + set.size());
    set.add(new Subclass("007812"));
    System.out.println("Set size " + set.size());

    for(Subclass sub : set) {
      System.out.println(" sub acctNbr " + sub.getAcctNbr());
    }
  }
}

子类

public class Subclass implements Comparable<Subclass> {

  public Subclass(String acctNbr) {
    this.acctNbr = acctNbr;
  }
  private String acctNbr;
  public String getAcctNbr() {
    return this.acctNbr;
  }
  public int compareTo(Subclass other) {
    return this.getAcctNbr().compareTo(other.getAcctNbr());
  }

  public boolean equals(Subclass other) {
    if(other.getAcctNbr().equals(this.getAcctNbr()))
      return true;
    else
      return false;
  }
  public int hashCode() {
    return acctNbr.hashCode();
  }
}

此代码输出

sross@sross-workstation:~/Documents$ javac testing/Subclass.java
sross@sross-workstation:~/Documents$ javac tester.java
sross@sross-workstation:~/Documents$ java tester
Set size 2
Set size 3
 sub acctNbr 007812
 sub acctNbr 007812
 sub acctNbr 007813
sross@sross-workstation:~/Documents$
有帮助吗?

解决方案

您需要重写equals(Object)。相反,这样做的你已经实现了与签名equalsequals(Subclass)方法。因此你HashSet使用上equals(Object)相等测试中定义的默认Object方法。

默认equals(Object)实现是基于对象的身份,并因此设定“允许”你添加两个Strings的是,尽管在语义上相等,都没有相同的对象。

其他提示

您没有正确地覆盖Object.equals()

@Override
public boolean equals(Object other) {
    if ((other == null) || !(other instanceof Subclass)) {
        return false;
    }
    return ((Sublcass) other).getAcctNbr().equals(this.getAcctNbr());
}

的方法boolean equals(Subclass other)创建第二方法,该方法是不是你打算做。

双元分:

首先,让每一个您认为您覆盖方法使用时间的@Override习惯。这会造成你的示例代码编译失败,导致你发现问题。

第二,如果您使用的是IDE,并没有突出了你一个很好的大胆的警告,它是配置错误!你应该修复它!

如果你不使用的IDE - 你真的应该。只要你键入public boolean equals(Subclass other),文字会改变颜色,将显示一个警告信息,告诉你自己可能的问题是什么。

顺便说一下,我已经上会聚为equals()标准成语是这样的:

@Override public boolean equals(Object object) {
  if (object instanceof Subclass) {
    Subclass that = (Subclass) object;
    return this.anInt == that.anInt
        && this.aString.equals(that.aString); // for example
  }
  return false;
}

部分的情况下,这是值得前置一个if (object == this) { return true; }但它真的不值得做的是日常习惯。

我几乎同样的问题,因为大家都在说你需要重写正确public boolean equals(Object o)方法。但是,这还不够!

另外,也需要覆盖public int hashCode()(如你所做的那样),否则,JAVA不会调用equals方法都没有。

第一个猜测,它看起来像你的equals(Subclass other)应该以覆盖equals(Object other)方法,只要你想被java.lang.Object.equals()。可能是集调用底层equals()实现。

您equals方法不会被调用。 equals的签名要求其采取Object,而不是一些其他类(包括任何类恰好是实施equals)。

public boolean equals(Object other) {
    ...
}
许可以下: CC-BY-SA归因
不隶属于 StackOverflow
scroll top