Skip to main content

Command Palette

Search for a command to run...

14. BASICS | Shallow Copy vs Deep Copy

This article will talk about shallow copy vs deep copy in javascript.

Updated
4 min readView as Markdown
S
Full-Stack Developer with 4 years' experience, specializing in backend development. Skilled in JavaScript, React, Python, Databases, and AWS. Known for building scalable web apps, leading teams, and maintaining strong client communication. Upskilling in Generative AI.

In JavaScript, the key difference between shallow and deep copies lies in how they handle nested objects. A shallow copy duplicates only the top-level properties, sharing references to nested objects, while a deep copy creates a completely independent clone of the entire structure, including all nested objects.


Shallow Copy

A shallow copy creates a new object (at different memory address) but only copies the values of the top-level properties. If any property value is an object (object literal or array), only the reference to that nested object is copied, not the nested object itself.

// ===================================================================
// Object literals
// ===================================================================
// 1) Simple object literal (no nesting)
const user1 = {firstName: 'Shubham', lastName: 'Agrawal', age: 25};

// Methods to create Shallow Copy
// Method 1: Object.assign()
const user2 = {};
Object.assign(user2, user1);

// Method 2: Spread operator
const user2 = { ...user1 };

console.log(user1 === user2); // ❌ false, because both have different memory address

// Now, mutate the copied object
user2.isLoggedIn = false;
console.log(user2);
/*
Output:
{firstName: 'Shubham', lastName: 'Agrawal', age: 25, isLoggedIn: false}
*/

console.log(user1);
/*
Output:
{firstName: 'Shubham', lastName: 'Agrawal', age: 25}
*/


// 2) Nested object literal
const user1 = {
  firstName: 'Shubham',
  lastName: 'Agrawal',
  age: 25,
  pata: {
    city: 'Delhi',
    pincode: 989888,
  },
  subject: ['Physics', 'CS', 'Math']
};

const user2 = { ...user1 };

console.log(user1 === user2); // ❌ false (different objects)
console.log(user1.pata === user2.pata); // ✅ (same nested reference)
console.log(user1.subject === user2.subject); // ✅ (same nested reference)

// Now, mutate the nested object in user2
user2.pata.city = "Mumbai";

console.log(user1.pata.city); 
// Output: Mumbai (Original object is affected)

console.log(user2.pata.city); // Output: Mumbai

user2.subject.push("Economics");
console.log(user1.subject); 
// Output: ['Physics', 'CS', 'Math', 'Economics'] (Original object is affected)


// ===================================================================
// Arrays
// ===================================================================
// 1) Simple array (no nesting)
const fruits = ['Mango', 'Apple', 'Orange'];

// Methods to create Shallow Copy
// Method 1: Object.assign()
const myFruits = [];
Object.assign(myFruits, fruits);

// Method 2: Spread operator
const myFruits = [...fruits];

// Method 3: concat()
const myFruits = [].concat(fruits)

// Method 4: slice()
const myFruits = fruits.slice()

console.log(fruits === myFruits); 
// Output: false, because both have different memory address

// Now, mutate the copied object
myFruits.push('Grapes', 'Dates');

console.log(myFruits); 
// Output: ['Mango', 'Apple', 'Orange', 'Grapes', 'Dates']
console.log(fruits); // Output: ['Mango', 'Apple', 'Orange']


// 2) Nested array (no nesting)
const fruits = ['Mango', 'Apple', 'Orange', [3, 4, 5]];
const myFruits = [...fruits];

// Now mutate the nested array in myFruits
delete myFruits[3][0];

console.log(myFruits); 
// Output: ['Mango', 'Apple', 'Orange', [empty, 4, 5]]
console.log(fruits); 
// Output: ['Mango', 'Apple', 'Orange', [empty, 4, 5]] (Original object is affected)

Deep Copy

A deep copy creates a completely independent clone, ensuring all nested objects are copied recursively, so modifications to the copy do not affect the original.

// ===================================================================
// Object literals
// ===================================================================
const original = {
  name: "Shubham",
  address: { city: "Jaipur" }
};

// Methods to create Deep Copy
// Method 1: structuredClone()
const deepCopy = structuredClone(original);

// Method 2: JSON methods
const deepCopy = JSON.parse(JSON.stringify(original));

console.log(original === deepCopy); // ❌ false (completely new object)
console.log(original.address === deepCopy.address); // ❌ false (nested object also copied)


// ===================================================================
// Arrays
// ===================================================================
const original = [
  { id: 1, name: "Shubham" },
  { id: 2, name: "Raj" }
];

// Methods to create Deep Copy
// Method 1: structuredClone()
const deepCopy = structuredClone(original);

// Method 2: map()
const deepCopy = original.map(item => ({ ...item }));

// Now, mutate the deep copy
deepCopy[0].name = "Aman";

console.log(original[0].name); // ✅ "Shubham" → original not affected
console.log(deepCopy[0].name); // ✅ "Aman"

Happy reading!