以下情况的hashCode()方法:当两个集合至少有一个共同的元素时,它们是相等的?

时间:2017-01-25 20:27:35

标签: java equals hashcode

我目前面临的情况是我有String元组(大小为2),如果两个元组至少有一个共同的元素,则应该认为它们是相等的。我有以下课程实现这个想法:

public class MyTuple
{
    private List<String> list = Arrays.asList(new String[2]);

    public List<String> getList()
    {
        return list;
    }

    public void set(String firstElement, String secondElement)
    {
        list.set(0, firstElement);
        list.set(1, secondElement);
    }

    @Override
    public boolean equals(Object other)
    {
        if (other instanceof MyTuple) {
            return !Collections.disjoint(this.list, ((MyTuple) other).getList());
        }
        return false;
    }
}

但是,根据hashCode()合同:

  

如果两个对象根据equals(Object)方法相等,则对两个对象中的每一个调用hashCode()方法必须生成相同的整数结果。

如何覆盖我的hashCode()方法以免违反合同?

1 个答案:

答案 0 :(得分:5)

在考虑hashCode()之前,我认为您应首先重新考虑equals()的设计。我不认为你可以实施equals()并履行所需的合同 - 尤其是关于传递性的合同

来自:Java Doc of Object#equals()

  

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

     
      
  • 它是自反的:对于任何非空引用值x,x.equals(x)   应该回归真实。

  •   
  • 它是对称的:对于任何非空参考值   当且仅当y.equals(x)时,x和y,x.equals(y)应该返回true   返回true。

  •   
  • 它是传递性的:对于任何非空参考值x,   y和z,如果x.equals(y)返回true而y.equals(z)返回true,   那么x.equals(z)应该返回true。

  •   
  • 这是一致的:对任何人而言   非空引用值x和y,x.equals(y)的多次调用   如果不是,则始终返回true或始终返回false   在对象的等比较中使用的信息被修改。

  •   
  • 对于   任何非空引用值x,x.equals(null)都应返回false。
  •   

为什么呢?我可以构建MyTuple的三个对象:

  • A = {x1,x2}
  • B = {x2,x3}
  • C = {x3,x4}

其中x1x2x3x4都是截然不同的。现在我有了

  • A.equals(B)返回true
  • B.equals(C)返回true
  • C.equals(A)返回false

他们违反了关于及物性的合同。

我认为您应该考虑使用自己的另一种关系(也许是partialEquals()),这样您就不必遵守合同。但是之后 您还无法使用equals()等方法并期望MyTuple工作, 例如,在HashMapHashSet