React’s Virtual DOM is one of the most talked-about concepts in frontend development.
People often hear:
“React is fast because of the Virtual DOM.”
But what does that actually mean?
The Virtual DOM is not magic. It is simply an optimization strategy React uses to efficiently update the UI without making unnecessary changes to the browser’s Real DOM.
To understand how React works internally, we first need to understand the problem React is trying to solve.
The Problem with Direct DOM Manipulation
The browser’s Real DOM is expensive to update frequently.
Whenever the DOM changes, the browser may need to:
Recalculate layout
Recompute styles
Repaint elements
Reflow the page structure
Even small changes can become expensive when repeated many times.
For example:
const title = document.getElementById("title");
title.innerText = "Updated Title";
This looks simple, but internally the browser may perform several rendering operations.
If an application updates the DOM repeatedly, performance starts degrading.
This became a major problem in large interactive applications.
React introduced the Virtual DOM to solve this efficiently.
Real DOM vs Virtual DOM
| Real DOM | Virtual DOM |
|---|---|
| Actual browser DOM | Lightweight JavaScript representation |
| Expensive to update | Cheap to create and compare |
| Directly changes UI | Calculates changes first |
| Managed by browser | Managed by React |
| Slower for frequent updates | Optimized for frequent updates |
The Virtual DOM is basically a lightweight JavaScript copy of the UI.
Instead of updating the Real DOM immediately, React first works with the Virtual DOM.
What Exactly is the Virtual DOM?
Consider this React component:
function App() {
return <h1>Hello World</h1>;
}
Internally, React converts this into a JavaScript object representation.
Conceptually, it looks something like this:
{
type: "h1",
props: {
children: "Hello World"
}
}
This object is a Virtual DOM node.
React creates an entire tree of such objects.
Initial Render Process in React
When a React application loads for the first time, React performs an initial render.
Step 1: Component Executes
function App() {
return <h1>Hello World</h1>;
}
React executes the component function.
Step 2: Virtual DOM Tree is Created
React creates a Virtual DOM tree.
App
└── h1
└── "Hello World"
Step 3: React Creates Real DOM Nodes
React converts the Virtual DOM into actual browser DOM elements.
<h1>Hello World</h1>
The browser finally paints the UI on the screen.
Diagram: Initial Render Flow
Component
↓
Virtual DOM Tree
↓
React Converts It
↓
Real DOM
↓
Browser Paints UI
What Happens When State or Props Change?
Suppose we have a counter component:
function Counter() {
const [count, setCount] = useState(0);
return <h1>{count}</h1>;
}
When this runs:
setCount(1);
React starts a re-render cycle.
However, React does not immediately update the browser DOM.
Instead, React follows a process.
How State or Props Change Triggers Re-render
When state or props change:
React re-executes the component
A new Virtual DOM tree is created
React compares the old and new trees
It finds the minimum required changes
Only those changes are applied to the Real DOM
This comparison process is called reconciliation.
Creation of a New Virtual DOM Tree
Suppose the old tree is:
h1 → "0"
After updating state:
h1 → "1"
React now compares these two trees.
What Diffing (Reconciliation) Means
Diffing is the process of comparing:
Old Virtual DOM tree
New Virtual DOM tree
React checks:
Did the element type change?
Did props change?
Did text content change?
Did children change?
Instead of rebuilding the entire UI, React calculates only the differences.
This process is called reconciliation.
How React Finds Minimal Required Changes
Consider this example.
Old DOM:
<h1>0</h1>
New DOM:
<h1>1</h1>
React notices:
The element type is still
h1Only the text content changed
So React updates only the text node.
It does not recreate the entire <h1> element.
This reduces unnecessary DOM operations.
Updating Only Changed Nodes in the Real DOM
After diffing, React applies the minimal required updates.
Instead of rebuilding the whole UI:
Only changed nodes are updated
Unchanged elements remain untouched
This makes updates much more efficient.
Example Update Flow
Before Update
Virtual DOM
└── h1 → "0"
After State Update
New Virtual DOM
└── h1 → "1"
Diffing Result
Only text content changed
Real DOM Update
<h1>1</h1>
Why This Approach Improves Performance
DOM operations are expensive.
JavaScript object operations are comparatively cheap.
React reduces performance cost by:
Performing comparisons in JavaScript
Avoiding unnecessary DOM updates
Updating only modified elements
Instead of:
Many expensive DOM updates
React performs:
Cheap comparisons
+
Minimal DOM updates
This is the core performance advantage of the Virtual DOM.
High-Level React Render → Diff → Commit Flow
React’s update lifecycle can be simplified into three major phases.
1. Render Phase
React executes components and creates a new Virtual DOM tree.
Component Runs
↓
New Virtual DOM Generated
2. Diff Phase (Reconciliation)
React compares:
Previous Virtual DOM tree
New Virtual DOM tree
Then calculates the differences.
Old Tree vs New Tree
↓
Difference Detection
3. Commit Phase
React applies minimal updates to the Real DOM.
Apply Minimal Changes
↓
Browser Updates UI
Full React Update Lifecycle Diagram
State / Props Change
↓
Component Re-renders
↓
New Virtual DOM Created
↓
Diffing / Reconciliation
↓
Minimal Changes Calculated
↓
Real DOM Updated
↓
Browser Paints Changes
Important Clarification
The Virtual DOM does not replace the Real DOM.
The browser UI can only be updated through the Real DOM.
The Virtual DOM is simply React’s strategy for deciding:
What changed
What actually needs updating
What can remain untouched
It acts as an optimization layer between React components and the browser.
Why React Became Popular Because of This
Before React:
Developers manually manipulated the DOM
UI updates became difficult to manage
Large applications suffered performance issues
React introduced:
Declarative UI
Predictable rendering
Efficient updates using reconciliation
Developers only describe what the UI should look like.
React figures out how to update it efficiently.
Final Mental Model
React follows this process:
UI Changes
↓
Create New Virtual DOM
↓
Compare with Old Virtual DOM
↓
Find Smallest Difference
↓
Update Only Necessary Real DOM Nodes
That is the core idea behind how React Virtual DOM works under the hood.
Additional Notes
Why Keys Matter in Lists
When rendering lists:
{todos.map(todo => (
<Todo key={todo.id} />
))}
Keys help React identify:
Which item changed
Which item moved
Which item was removed
Without proper keys, React may perform unnecessary re-renders.
Virtual DOM is Not the Only Optimization Strategy
Modern frameworks use different rendering approaches.
For example:
React uses Virtual DOM
Svelte compiles updates directly
SolidJS uses fine-grained reactivity
React’s strength is not only performance.
Its major strengths are:
Predictable UI updates
Large ecosystem
Reusable component architecture
Developer experience
Conclusion
The Virtual DOM is React’s smart update mechanism.
Instead of directly manipulating the browser DOM repeatedly, React:
Creates a Virtual DOM representation
Generates a new tree after updates
Compares old vs new trees
Finds minimal differences
Updates only necessary parts of the Real DOM
This makes React applications more efficient, scalable, and easier to maintain.
Understanding this render → diff → commit lifecycle gives a strong mental model for how React works internally.
Comments
Join the discussionNo comments yet. Be the first to comment.