如何从三个长整型生成哈希码

发布于 2024-11-02 11:31:35 字数 318 浏览 4 评论 0原文

我有一个以坐标为键的 HashMap。

坐标有 3 个长整型,分别保存 x、y 和 z 坐标。 (坐标是并且需要是自定义类,坐标需要是长整型)。

现在我希望能够通过执行以下操作来访问字段 [5, 10, 4]:hashMap.get(new Cooperative(5, 10, 4))

我已经实现了 equals 方法,但这还不够,因为显然我还需要提供 hashCode 的实现。所以我的问题是如何从三个 long 生成唯一的 hashCode?。

附加:使用外部库中的哈希生成器不是一种选择。

I have a HashMap with coordinates as keys.

Coordinates have 3 longs holding the x, y and z coordinate. (Coordinate is and needs to be a custom class, the coordinates need to be longs).

Now i want to be able to access e.g. the field [5, 10, 4] by doing: hashMap.get(new Coordinate(5, 10, 4)).

I have implemented the equals method but that is not enough since apparently i need to provide an implementation for hashCode as well. So my question is how do i generate an unique hashCode from three longs?.

Additional: Using a hash generator from an external library is not option.

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(5

雨轻弹 2024-11-09 11:31:35

Joshua Bloch 在第 3 章 他的《Effective Java》。

像这样:

public class Coordinate
{
    private long x;
    private long y;
    private long z;

    @Override
    public boolean equals(Object o)
    {
        if (this == o) return true;
        if (o == null || getClass() != o.getClass()) return false;

        Coordinate that = (Coordinate) o;

        if (x != that.x) return false;
        if (y != that.y) return false;
        if (z != that.z) return false;

        return true;
    }

    @Override
    public int hashCode()
    {
        int result = (int) (x ^ (x >>> 32));
        result = 31 * result + (int) (y ^ (y >>> 32));
        result = 31 * result + (int) (z ^ (z >>> 32));
        return result;
    }
}

Joshua Bloch tells you how to write equals and hashCode for your Coordinate class in chapter 3 of his "Effective Java".

Like this:

public class Coordinate
{
    private long x;
    private long y;
    private long z;

    @Override
    public boolean equals(Object o)
    {
        if (this == o) return true;
        if (o == null || getClass() != o.getClass()) return false;

        Coordinate that = (Coordinate) o;

        if (x != that.x) return false;
        if (y != that.y) return false;
        if (z != that.z) return false;

        return true;
    }

    @Override
    public int hashCode()
    {
        int result = (int) (x ^ (x >>> 32));
        result = 31 * result + (int) (y ^ (y >>> 32));
        result = 31 * result + (int) (z ^ (z >>> 32));
        return result;
    }
}
迷爱 2024-11-09 11:31:35

这是一个老问题,但如果有人遇到它,现在有一个更简单的方法来做到这一点:

@Override 
public int hashCode() {
    return Objects.hash(x, y, z);
}

This is an old question, but if anyone bumps into it, now there is an easier way to do it:

@Override 
public int hashCode() {
    return Objects.hash(x, y, z);
}
各自安好 2024-11-09 11:31:35

在 Java 中,标准 hashCode() 方法返回 int,它是 32 位。

long 数据类型是 64 位。因此,三个long意味着192位信息,当然不能通过任何哈希函数将其唯一映射为仅仅32位的哈希值。

然而,HashMap 不需要唯一的散列,它只会在发生冲突时对其进行处理。

一种简单的方法是构建字符串,即“x,y,z”,然后对字符串进行哈希处理。

您也可以尝试将这些值异或:在一起:

int hashCode()
{
  return (int) (x ^ y ^ z);
}

In Java, the standard hashCode() method returns int, which is 32 bits.

The long datatype is 64 bits. Therefore, three longs means 192 bits of information, which of course cannot be uniquely mapped into just 32 bits of hash value by any hash function.

However, a HashMap will not require unique hashing, it will simply handle the collisions when they occur.

A naive way would be to build the string, i.e. "x,y,z", then hash the string.

You could also try just XOR:ing the values together:

int hashCode()
{
  return (int) (x ^ y ^ z);
}
生活了然无味 2024-11-09 11:31:35

如何生成唯一的 hashCode
从三个长?

你不需要。哈希码不需要是唯一的。

how do i generate an unique hashCode
from three longs?

You don't need to. Hash codes are not required to be unique.

自由范儿 2024-11-09 11:31:35

您应该意识到哈希码和 HashMap 中使用的唯一键之间存在差异。

坐标类的哈希码根本不必是唯一的...

哈希码的一个好的解决方案是:

(int)(x ^ (x >> 32) ^ y ^ (y >> 32) ^ z ^ (z >> 32));

将每个长整型的两半进行异或运算。

You should realize there is a difference between a hashcode and the unique key to be used in a HashMap.

The hashcode for your Coordinate class does not have to be unique at all...

A good solution for the hashcode would be:

(int)(x ^ (x >> 32) ^ y ^ (y >> 32) ^ z ^ (z >> 32));

Wich is the XOR of the two halves of each of the longs XOR-ed together.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文