简体   繁体   English

Java中空对象的哈希码必须是什么?

[英]what must be hashcode of null objects in Java?

According to a comment from this post , hascode of null objects can throw NPE or a value of zero .根据这篇文章的评论, null objectshascode可以throw NPEzero This is implementation specific.这是特定于实现的。 but within the same implementation, why does Objects.hashcode and hascode(instance) return different values.但在同一个实现中,为什么Objects.hashcodehascode(instance)返回不同的值。 for ex:例如:

public class EqualsTesting {

    public static void main(String[] args){
        String p1 =null;
        String p2 = null;
        System.out.println(Objects.hashCode(p1));
        System.out.println(p2.hashCode());

    }
}

Output:输出:

0
Exception in thread "main" java.lang.NullPointerException
    at BinaryTrees.EqualsTesting.main(EqualsTesting.java:14)

If this is the case, will this not affect the key look-up in HashMap where null Key-value pairs are allowed.如果是这种情况,这不会影响HashMap中允许null Key-value pairskey look-up (It might either hash to bucket 0 or throw a NPE ) (它可能会hashbucket 0throw a NPE

How would you calculate hashCode of an object that doesn't even exists?你将如何计算一个甚至不存在的对象的hashCode When p2 is null , invoking any method on it will throw a NPE .p2null时,对其调用任何方法都会引发NPE That isn't giving you any particular value of a hashCode.这并没有给你任何特定的 hashCode 值。

Objects.hashCode() is just a wrapper method, which performs a pre-check for null values, and for reference that is not null , it returns the same value as p2.hashCode() as in this case. Objects.hashCode()只是一个包装器方法,它对null值执行预检查,对于非null的引用,它返回与p2.hashCode()相同的值,就像在这种情况下一样。 Here's the source code of the method:这是该方法的源代码:

public static int hashCode(Object o) {
    return o != null ? o.hashCode() : 0;
}

If you will search around, you'll notice that HashMap has a special handling for null keys.如果您四处搜索,您会注意到HashMapnull键有特殊处理 null values are fine as you don't compute hash code for them in a HashMap . null值很好,因为您不在HashMap中为它们计算哈希码。 This is the reason why null keys work fine in HashMap .这就是null键在HashMap中工作正常的原因。 As to why Objects.hashCode works fine, take a look at Rohit's answer.至于为什么Objects.hashCode工作正常,看看 Rohit 的回答。

As the javadoc says:正如javadoc所说:

Objects.hashCode(Object o) Objects.hashCode(对象 o)

Returns the hash code of a non-null argument and 0 for a null argument.返回非空参数的哈希码,空参数返回 0。

p2.hashCode() throws a NullPointerException because you are trying to access a method of a null object. p2.hashCode()抛出NullPointerException因为您试图访问空对象的方法。

According to a comment from this post, hascode of null objects can throw NPE or a value of zero.根据这篇文章的评论,空对象的 hascode 可以抛出 NPE 或零值。

That is not true.那不是真的。 (And it is not what @Bohemian's comment is saying!) (这不是@Bohemian 的评论所说的!)

What happens in HashMap and HashSet is that they treat null as a special case. HashMapHashSet中发生的事情是它们将null视为一种特殊情况。 Instead of calling hashcode() on the null object (which would NPE!!), they use zero in as a hard-coded alternative hashcode.他们没有在null对象上调用hashcode() (这将是 NPE !!),而是使用零作为硬编码的替代哈希码。

I stress ... this is special case behaviour of HashMap and HashSet ... not hashcode() .我强调......这是HashMapHashSet的特殊情况行为......不是hashcode()

As your example shows, if you do attempt to call the hashcode() method on null , you will get an NPE.如您的示例所示,如果您确实尝试在null上调用hashcode()方法,您获得 NPE。 The JLS says that that is what will happen ... and it happens whenever you try to invoke any instance method on null . JLS 说这将发生......每当您尝试在null上调用任何实例方法时都会发生这种情况。

(On the other hand, the Objects.hashCode(obj) method does deal with the case where obj is null as a special case. And that's the whole point of the static method!) (另一方面, Objects.hashCode(obj)方法确实objnull的情况作为一种特殊情况处理。这就是静态方法的重点!)

The hash code of null is 0 (see Objects.hash() ) null的哈希码为 0(参见Objects.hash()

    public static int hashCode(Object a[]) {
        if (a == null)
            return 0;

        int result = 1;

        for (Object element : a)
            result = 31 * result + (element == null ? 0 : element.hashCode());

        return result;
    }

0 is hard coded value for null in Hashmap. 0 是 Hashmap 中null的硬编码值。 You can see the following actual implementations done in HashMap and Objects java classes.您可以在 HashMap 和 Objects java 类中看到以下实际实现。

from HashMap.java来自HashMap.java

static final int hash(Object key) {
        int h;
        return (key == null) ? 0 : (h = key.hashCode()) ^ (h >>> 16);
    }

from Object.java来自Object.java

public static int hashCode(Object o) {
        return o != null ? o.hashCode() : 0;
    }

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

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