We will explore the concepts of Pass by Value, Pass by Reference.
Before moving on to the concepts , let’s revise basics of primitive type and non primitive types.
Basically, we’ve all come across things like numbers, strings, booleans, objects, arrays, and functions in JavaScript. Numbers, strings, and booleans just hold a specific value, which is pretty straightforward. The size is fixed.
let a=103123;
But when it comes to objects, arrays, and functions, the amount of data they hold isn’t fixed—it’s dynamic. For example, I can create an array and keep adding endless elements into it.
let arr = [];
arr.push(1, 2, 3, 4, 5, 6); // Keeps expanding in memory
let person1 = { name: "Raghav",
age: 20.... //can keep on adding
};
Now, let’s talk about memory management.
All the variables and values are generally stored in two types of data structures: stack and heap.
Stack is a data structure with a limited size.
Heap allows dynamic allocation, meaning data can be added as much as needed.
At the same time , there is a tradeoff.
Since the stack has a fixed size, it’s faster to find, check, and change data.
in the heap, where data is scattered and grows freely, finding something takes more time
You can imagine the heap like Doraemon's magic tummy (4D pocket)—it can store unlimited items, no matter how big they are. But finding something takes time. 🎒✨
Meanwhile, the stack is like Nobita’s school bag—it has limited space, but he can quickly grab his books when needed. 📚⚡
Every program has both fixed-size values (like numbers and strings) and dynamic structures (like arrays and objects).
If everything was stored in stack directly with its variable name and value, it would create huge overhead, especially for objects, arrays, and functions since their size is dynamic and keeps expanding.
But the stack has limited space—if it exceeds a certain point, it results in a stack overflow !!!!.
📚 If Nobita tries to stuff too many books into his bag, it will overflow!
So, how do we store bigger elements like objects and arrays? 🤔
The first idea was to store larger objects in the heap and smaller values (like numbers and booleans) in the stack. But,
- 🔍 Imagine you have a massive room with 1000 books. If you need one specific book, you might have to search through all 999 books before finding it—which takes too long!
💡 Can we make this more efficient?
Instead of searching randomly across the whole room, we can keep a small list (stack) storing the address of each book. Since the address is fixed, we don’t have to search blindly. We can go directly to the book’s location in the room and get it instantly.
This way, we combine the best of both worlds—quick access from the stack and flexible storage in the heap! 🚀
That’s why JavaScript handles memory differently for these two types:
(numbers, strings, booleans, etc.) are stored directly in the stack since their size is fixed.
(objects, arrays, functions) are stored in the heap, while only a reference (memory address) is kept in the stack.
Here is a diagram showing how does it appear.
Primitive Vs Non -Primitive
Since now you have a solid understanding of how the memory works .It is easier to understand these 4 2 technical jargons.
Primitive - The elements which were directly stored in the stack(numbers, strings, booleans, etc.)
Non- Primitive -The elements which were stored in the heap with address in stack (objects, arrays, functions etc)
Pass-By-Value VS Pass-By-Reference
let a=5;
b=a;
b=10;
console.log(b) //10
console.log(a) //5
Let’s understand how this happened
a = 5
is stored at address0x100
since it is primitive(Int).let a=5;
b
is assigned a new address0x101
.b=a;
b
goes toa
's address (0x100
), fetches the value5
, and stores it at0x101
.b=a;
b
updates its value to10
at address0x101
.b=10;
a
remains unchanged at0x100
.
In this case, b
is assigned a copy of the value stored in a
(5), so when b
is modified to 10, it doesn't affect a
, which means this is pass by value.
Generally ,Primitive assignments means pass-by-value.
Consider this case now.
let a = {name: "Raghav"};
let b = a;
b.name = "Rahul"; // obj2 is modified, and obj1 also changes
console.log(a.name); // "Rahul"
console.log(b.name); // "Rahul"
Let’s anaylse.
a = {name: "Raghav"}
creates an object at heap address0x201
. a is stored at the address 0×100.a
points to0x201
in the stack.b = a
assignsb
the same address0x201
.b.name
= "Rahul"
modifies the object at0x201
in the heap.
In this case, b
is assigned a address of the value stored in a
so when b
is modified to “Rahul” it affects a
, which means this is pass by reference.
Generally , Non-Primitive assignment means pass-by-reference.
In the next article we will discuss about concepts such as shallow and deep copying , serialization and deserialization.
Thankyou!!l