To begin with it's crucial to understand that manipulating the DOM is one the most costliest operations that the browser engine has to perform. It's comparatively very easy to create tens of objects or do lot of JavaScript operations than to manipulate DOM. The goal of any Frontend framework/library is to abstract this problem away from developer and provide the course to focus on UI implementation details.
React has such a popularity because of the way it takes care of this DOM updating problem. So let's try to understand how React solves this problem and what we as developers need to know about this process to make the best of what it offers.
To begin with, React maintains a visual representation of the UI in the memory - what is popularly know as the Virtual DOM. Now when there is a change in the state of a component, React creates a new virtual DOM with the new changes applied. Now ReactJS maintains two virtual DOM, one with the updated state Virtual DOM and other with the previous state Virtual DOM.
React compares the two virtual DOMs to identify the minimal changes that have to be applied to the real DOM. Now this process of comparing the two trees to determine the parts of the real DOM to be updated is called Reconciliation.
Finding the difference between both the tree takes a complexity of O(n ^ 3) for best of the algorithms. Instead, React implements a heuristic O(n) algorithm based on two assumptions:
Two elements of different types will produce different trees.
- When React finds that 2 root elements of the same level have different type, it completely discards the tree and rebuilds it from scratch i.e. if React finds a
<div>
instead of<section>
during the diffing, React shall build the tree newly again. - If React finds that the attribute of an element has changed for the root element, then only that property will be updated in the real DOM
- When React finds that 2 root elements of the same level have different type, it completely discards the tree and rebuilds it from scratch i.e. if React finds a
The developer can hint at which child elements may be stable across different renders with a key prop.
- React compares each child and generates the diff to be applied.
- But what if a child was added to top the list? React detects difference for each child and creates mutations to be applied for each of them.
//Before
<div>
<div>Item 1</div>
<div>Item 2</div>
</div>
//After
<div>
<div>Item 3</div>
<div>Item 1</div>
<div>Item 2</div>
</div>
- To overcome this inefficiency, React recommends developers to add a
key
property to the children, to help the algorithm identify differenced based on it.
//After
<div>
<div key=3>Item 3</div>
<div key=1>Item 1</div>
<div key=2>Item 2</div>
</div>
Once React has the list of changes, it will apply the required changes to the real DOM. Fiber is the name of the new reconciliation algorithm used in react.
To sum up, React efficiently takes care of applying the DOM with minimal changes that occurred during the update. It is important to understand the details to consider while managing React elements, so it will be easier and much efficient for React to apply changes giving the best possible results.
Happy coding! ✨
If you found this article useful follow me on LinkedIn & Twitter to be part of my journey.
References: