Question

According to a comment from this post, hascode of null objects can throw NPE or a value of zero. This is implementation specific. but within the same implementation, why does Objects.hashcode and hascode(instance) return different values. 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. (It might either hash to bucket 0 or throw a NPE)

Was it helpful?

Solution

How would you calculate hashCode of an object that doesn't even exists? When p2 is null, invoking any method on it will throw a NPE. That isn't giving you any particular value of a 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. Here's the source code of the method:

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

OTHER TIPS

If you will search around, you'll notice that HashMap has a special handling for null keys. null values are fine as you don't compute hash code for them in a HashMap. This is the reason why null keys work fine in HashMap. As to why Objects.hashCode works fine, take a look at Rohit's answer.

As the javadoc says:

Objects.hashCode(Object o)

Returns the hash code of a non-null argument and 0 for a null argument.

p2.hashCode() throws a NullPointerException because you are trying to access a method of a null object.

According to a comment from this post, hascode of null objects can throw NPE or a value of zero.

That is not true. (And it is not what @Bohemian's comment is saying!)

What happens in HashMap and HashSet is that they treat null as a special case. Instead of calling hashcode() on the null object (which would NPE!!), they use zero in as a hard-coded alternative hashcode.

I stress ... this is special case behaviour of HashMap and HashSet ... not hashcode().

As your example shows, if you do attempt to call the hashcode() method on null, you will get an NPE. The JLS says that that is what will happen ... and it happens whenever you try to invoke any instance method on 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!)

The hash code of null is 0 (see 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. You can see the following actual implementations done in HashMap and Objects java classes.

from HashMap.java

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

from Object.java

public static int hashCode(Object o) {
        return o != null ? o.hashCode() : 0;
    }
Licensed under: CC-BY-SA with attribution
Not affiliated with StackOverflow
scroll top