简体   繁体   English

具有两个没有顺序的字段的唯一hashCode

[英]Unique hashCode with two fields without order

I need a hashCode implementation in Java which ignores the order of the fields in my class Edge . 我需要Java中的hashCode实现,它忽略了我的类Edge字段的顺序。 It should be possible that Node first could be Node second, and second could be Node first. Node首先可能是Node第二个,第二个可能是Node第一个。

Here is my method is depend on the order: 这是我的方法取决于顺序:

public class Edge {
    private Node first, second;

    @Override
    public int hashCode() {
        int hash = 17;
        int hashMultiplikator = 79;
        hash = hashMultiplikator * hash
                + first.hashCode();
        hash = hashMultiplikator * hash
                + second.hashCode();
        return hash;
    }
}

Is there a way to compute a hash which is for the following Edges the same but unique? 有没有办法计算一个哈希值,这个哈希值对于以下边缘是相同但唯一的?

Node n1 = new Node("a");
Node n2 = new Node("b");
Edge ab = new Edge(n1,n2);
Edge ba = new Edge(n2,n1);

ab.hashCode() == ba.hashCode() should be true . ab.hashCode() == ba.hashCode()应为true

You can use some sort of commutative operation instead of what you have now, like addition: 您可以使用某种可交换操作而不是现在的操作,例如:

@Override
public int hashCode() {
    int hash = 17;
    int hashMultiplikator = 79;
    int hashSum = first.hashCode() + second.hashCode();
    hash = hashMultiplikator * hash * hashSum;
    return hash;
}

I'd recommend that you still use the multiplier since it provides some entropy to your hash code. 我建议你仍然使用乘法器,因为它为你的哈希码提供了一些熵。 See my answer here , which says: 请参阅我的回答 ,其中说:

Some good rules to follow for hashing are: 哈希遵循的一些好规则是:

  • Mix up your operators. 混淆运营商。 By mixing your operators, you can cause the results to vary more. 通过混合运算符,可以使结果变化更大。 Using simply x * y in this test, I had a very large number of collisions. 在这个测试中使用简单的x * y ,我遇到了大量的碰撞。
  • Use prime numbers for multiplication. 使用素数进行乘法运算。 Prime numbers have interesting binary properties that cause multiplication to be more volatile. 素数具有有趣的二元属性,导致乘法更不稳定。
  • Avoid using shift operators (unless you really know what you're doing). 避免使用移位操作符(除非你真的知道你在做什么)。 They insert lots of zeroes or ones into the binary of the number, decreasing volatility of other operations and potentially even shrinking your possible number of outputs. 它们在数字的二进制数中插入了大量的零或1,减少了其他操作的波动性,甚至可能缩小了可能的输出数量。

To solve you problem you have to combine both hashCodes of the components. 要解决您的问题,您必须组合组件的两个hashCodes。

An example could be: 一个例子可能是:

@Override
public int hashCode() {
    int prime = 17;
    return prime * (first.hashCode() + second.hashCode());
}

Please check if this matches your requirements. 请检查这是否符合您的要求。 Also a multiplikation or an XOR insted of an addition could be possible. 此外,还可以进行多次加法或XOR加法。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM