Home > Blockchain >  Why will HashMap ignore entries with keys from the same Superclass?
Why will HashMap ignore entries with keys from the same Superclass?

Time:01-08

I have created a map with maps inside as a test and it seems that the outer map will ignore the rest of the maps. I assume it is overriding them. Also I presume that it is because they all extend from Map so it is treating them as the same instance when they are not.

Map<Map<Integer, String>,String> maps=new HashMap<>();
maps.put(new HashMap<Integer, String>(),"HashMap");
maps.put(new TreeMap<Integer, String>(),"TreeMap");
maps.put(new LinkedHashMap<Integer, String>(),"LinkedHashMap");
maps.put(new Hashtable<Integer, String>(),"Hashtable");

Printing the map to logs will show only the last one added:

maps: {{}=Hashtable}

I tried with other Map implementations and all have the same behavior except TreeMap which will throw an exception due to the fact that HashMap does not implement Comparable.

Is this expected behavior? Why does HashMap behave like this?

CodePudding user response:

When we take a look at the documentation of Map::equals, we see that this method

Returns true if the given object is also a map and the two maps represent the same mappings. More formally, two maps m1 and m2 represent the same mappings if m1.entrySet().equals(m2.entrySet()).

Due to the contract between Object::equals and Object::hashCode, this means that those maps will also have the same hash code. This, in return, means that they are, for Map::put, indistinguishable. Thus, each put(...) in the sample program overrides the previous put and thus results in a final map size of 1 with only the HashTable in the entrySet().

So yes, this is expected behaviour. And it is not only expected for HashMap, but for all Map implementations.

As was already pointed out in the comments by Pshemo, it is questionable to use a Map as key for another Map and, in general, we should use immutable objects as keys.

  •  Tags:  
  • Related