How to create a Copy of a Map in JavaScript

avatar

Borislav Hadzhiev

4 min

banner

Photo from Unsplash

Table of Contents #

  1. Create a Deep Copy of a Map in JavaScript
  2. Create a Deep Copy of a Map using lodash
  3. Create a shallow copy of a Map in JavaScript
  4. Create a shallow copy of a Map using Map.forEach

Create a Deep Copy of a Map in JavaScript #

To create a deep copy of a Map object:

  1. Convert the Map to an array.
  2. Use the JSON.stringify() method to stringify the array.
  3. Use the JSON.parse() method to parse the JSON string.
  4. Pass the result to the Map() constructor.
index.js
const existingMap = new Map([ ['address', {street: 'Example'}], ['numbers', [1, 2, 3]], ]); const deepCopy = new Map( JSON.parse( JSON.stringify(Array.from(existingMap)) ) ); // ๐Ÿ‘‡๏ธ {'address' => {street: 'Example'}, 'numbers': [1, 2, 3]} console.log(deepCopy);

We used the Array.from() method to convert the Map object to a two-dimensional array.

index.js
const existingMap = new Map([ ['address', {street: 'Example'}], ['numbers', [1, 2, 3]], ]); // ๐Ÿ‘‡๏ธ [['address', {street: 'Example}], ['numbers', [1, 2, 3]]] console.log(Array.from(existingMap));

The next step is to use the JSON.stringify method to convert the array to a JSON string.

index.js
const existingMap = new Map([ ['address', {street: 'Example'}], ['numbers', [1, 2, 3]], ]); // ๐Ÿ‘‡๏ธ '[["address",{"street":"Example"}],["numbers",[1,2,3]]]' console.log(JSON.stringify(Array.from(existingMap)));
Converting the array to a JSON string makes all the nested arrays and objects lose their reference.

We then used the JSON.parse method to parse the string back into an array.

index.js
const existingMap = new Map([ ['address', {street: 'Example'}], ['numbers', [1, 2, 3]], ]); // ๐Ÿ‘‡๏ธ [ [ 'address', { street: 'Example' } ], [ 'numbers', [ 1, 2, 3 ] ] ] console.log(JSON.parse(JSON.stringify(Array.from(existingMap))));

The last step is to pass the two-dimensional array to the Map() constructor.

The trick here is to stringify the array, using the JSON.stringify method, so that all nested objects lose their reference.

If we then try to mutate the array in the new Map, it wouldn't affect the existing Map.

index.js
const existingMap = new Map([ ['address', {street: 'Example'}], ['numbers', [1, 2, 3]], ]); const deepCopy = new Map(JSON.parse( JSON.stringify(Array.from(existingMap)) )); deepCopy.get('numbers').pop(); // ๐Ÿ‘‡๏ธ {'address' => {street: 'Example'}, 'numbers' => [1, 2]} console.log(deepCopy); // ๐Ÿ‘‡๏ธ {'address' => {'street':'Example'},'numbers' => [1, 2, 3]} console.log(existingMap);

We used the pop method to mutate the array in the deep copy, however, the array in the existing Map wasn't affected.

The nested arrays in the Maps have a different reference and location in memory because we used the JSON.stringify method.

If you have to create deep copies of Map objects often, define a reusable function.

index.js
function deepCopyMap(map) { return new Map(JSON.parse(JSON.stringify(Array.from(map)))); } const existingMap = new Map([ ['address', {street: 'Example'}], ['numbers', [1, 2, 3]], ]); const copy = deepCopyMap(existingMap); // ๐Ÿ‘‡๏ธ Map(2) { 'address' => { street: 'Example' }, 'numbers' => [ 1, 2, 3 ] } console.log(copy);

The function takes a Map object as a parameter and returns a deep copy of the Map.

Create a Deep Copy of a Map using lodash #

You can also use the lodash library to create a deep copy of a Map object.

First, install the lodash module if you haven't already.

shell
# ๐Ÿ‘‡๏ธ initialize a package.json file npm init -y npm install lodash

You can now import and use the lodash.cloneDeep method.

index.js
import _ from 'lodash'; const existingMap = new Map([ ['address', {street: 'Example'}], ['numbers', [1, 2, 3]], ]); const deepCopy = _.cloneDeep(existingMap); // ๐Ÿ‘‡๏ธ Map(2) { 'address' => { street: 'Example' }, 'numbers' => [ 1, 2, 3 ] } console.log(deepCopy);

The cloneDeep method takes a value and recursively clones it, returning the deep cloned value.

Mutating the array property in the cloned Map doesn't mutate the property in the original Map.

index.js
import _ from 'lodash'; const existingMap = new Map([ ['address', {street: 'Example'}], ['numbers', [1, 2, 3]], ]); const deepCopy = _.cloneDeep(existingMap); deepCopy.get('numbers').pop(); // ๐Ÿ‘‡๏ธ {'address' => {street: 'Example'}, 'numbers' => [1, 2]} console.log(deepCopy); // ๐Ÿ‘‡๏ธ {'address' => {'street':'Example'},'numbers' => [1, 2, 3]} console.log(existingMap);

We used the pop method to mutate the array in the deep copy, however, the array in the existing Map wasn't affected.

Create a shallow copy of a Map in JavaScript #

To create a shallow copy of a Map:

  1. Pass the existing Map as a parameter to the Map() constructor.
  2. The Map() constructor takes an iterable, such as another Map, and adds the key-value pairs of the iterable to the new Map.
index.js
const oldMap = new Map([ ['name', 'bobby hadz'], ['country', 'Chile'], ]); // ๐Ÿ‘‡๏ธ Map(2) { 'name' => 'bobby hadz', 'country' => 'Chile' } console.log(oldMap); const copy = new Map(oldMap); // ๐Ÿ‘‡๏ธ Map(2) { 'name' => 'bobby hadz', 'country' => 'Chile' } console.log(copy);

We used the Map() constructor to create a shallow copy of an existing Map.

The only parameter the constructor takes is an iterable, such as an array, or another Map.

The elements in the iterable should be key-value pairs, e.g. a two-dimensional array or another Map object.

index.js
const example1 = [ ['name', 'Tom'], ['country', 'Chile'], ]; const example2 = new Map([ ['name', 'Tom'], ['country', 'Chile'], ]);

Each key-value pair gets added to the new Map.

The new Map object has a completely different reference and location in memory.

Adding key-value pairs to it does not interact with the existing Map.

index.js
const oldMap = new Map([ ['name', 'bobby hadz'], ['country', 'Chile'], ]); // ๐Ÿ‘‡๏ธ Map(2) { 'name' => 'bobby hadz', 'country' => 'Chile' } console.log(oldMap); const copy = new Map(oldMap); // ๐Ÿ‘‡๏ธ Map(2) { 'name' => 'bobby hadz', 'country' => 'Chile' } console.log(copy); copy.set('age', 30); // ๐Ÿ‘‡๏ธ Map(3) { 'name' => 'bobby hadz', 'country' => 'Chile', 'age' => 30 } console.log(copy); // ๐Ÿ‘‡๏ธ Map(2) { 'name' => 'bobby hadz', 'country' => 'Chile' } console.log(oldMap);

The code sample shows that adding key-value pairs to the copy doesn't add key-value pairs to the original Map object.

You can also use the Map.forEach() method to create a shallow copy of a Map object.

Create a shallow copy of a Map using Map.forEach #

To create a shallow copy of a Map:

  1. Declare a new variable and initialize it to an empty Map.
  2. Use the Map.forEach() method to iterate over the existing Map.
  3. Use the Map.set() method to add each key-value pair to the new Map.
index.js
const oldMap = new Map([ ['name', 'bobby hadz'], ['country', 'Chile'], ]); const copy = new Map(); oldMap.forEach((value, key) => { copy.set(key, value); }); // ๐Ÿ‘‡๏ธ Map(2) { 'name' => 'bobby hadz', 'country' => 'Chile' } console.log(oldMap);

We used the Map() constructor to create an empty Map object.

The function we passed to the Map.forEach method gets called with each key-value pair of the Map object.

On each iteration, we use the Map.set method to add the current key-value pair to the new Map object.

I wrote a book in which I share everything I know about how to become a better, more efficient programmer.
book cover
You can use the search field on my Home Page to filter through all of my articles.

Copyright ยฉ 2023 Borislav Hadzhiev