Logo Questions Linux Laravel Mysql Ubuntu Git Menu
 

Deep copying a Java Map with values that are Sets

Tags:

java

hashmap

map

I have a map (Map<String, Set<String>>), and want to copy the map to a new map object. However, if I just feed the map to the say HashMap constructor (new HashMap<String, Set<String>>(oldMap)) it won't do a full copy, and only copies the reference to the set, which can be modified and those changes will be reflected in the new map.

Is there a more simply way of doing a full copy other than iterating over each key/value pair and creating a new HashSet for each set then adding that to the map?

like image 643
cole Avatar asked Dec 20 '13 16:12

cole


People also ask

How do I copy a HashMap without references?

Using Map. putAll() Instead of iterating through all of the entries, we can use the putAll() method, which shallow-copies all of the mappings in one step: HashMap<String, Employee> shallowCopy = new HashMap<>(); shallowCopy.

How do I copy values from one HashMap to another?

Given a HashMap, there are three ways one can copy the given HashMap to another: By normally iterating and putting it to another HashMap using put(k, v) method. Using putAll() method. Using copy constructor.


2 Answers

There was some discussion on this here for deep cloning:

Java HashMap - deep copy

It's hard in this situation though as the new map and set need to rebuild themselves. Do you also need to clone the contents of the Set? If so then you could just serialize then de-serialize the whole collection.

Iterating yourself will almost certainly be faster and will let you control how deep the cloning goes. Serializing will be slower but so long as everything in the object tree is serializable it will copy everything in the object tree and maintain things like circular references etc. (For example if you had 2 keys in the map pointing to the same Set object then iterating will split that into 2 sets, serializing will maintain the link).

like image 117
Tim B Avatar answered Sep 30 '22 13:09

Tim B


If you don't want to use external library and just want to copy this specific map you can do:

HashMap<String, HashSet<String>> copy = new HashMap<>();
for(String newKey : oldMap.keySet()){
    copy.put(newKey, new HashSet<String>(oldMap.get(newKey)));
}

Where oldMap is the map you are trying to copy. This worked for me.

like image 43
Moe Avatar answered Sep 30 '22 14:09

Moe