The **useEffect **Hook allows you to perform side effects in your components.
Some examples of side effects are:
- fetching data,
- directly updating the DOM,
- timers.
useEffect accepts two arguments. The second argument is optional.
useEffect(<function>, <dependency>)
Example:
Use setTimeout() to count 1 second after initial render
But wait!! It keeps counting even though it should only count once!
- useEffect runs on every render. That means that when the count changes, a render happens, which then triggers another effect.
- This is not what we want. There are several ways to control when side effects run.
We should always include the second parameter which accepts an array. We can optionally pass dependencies to useEffect in this array
So, to fix this issue, let's only run this effect on the initial render
Here is an example of a useEffect Hook that is dependent on a variable. If the count variable updates, the effect will run again:
import { useState, useEffect } from 'react';
import { createRoot } from 'react-dom/client';
function Counter() {
const [count, setCount] = useState(0);
const [calculation, setCalculation] = useState(0);
useEffect(() => {
setCalculation(() => count * 2);
}, [count]); // <- add the count variable here
return (
<>
<p>Count: {count}</p>
<button onClick={() => setCount((c) => c + 1)}>+</button>
<p>Calculation: {calculation}</p>
</>
);
}
createRoot(document.getElementById('root')).render(
<Counter />
);
if there are multiple dependencies, they should be included in the useEffect dependency array.
Effect Cleanup
Some effects require cleanup to reduce memory leaks.
Timeouts, subscriptions, event listeners, and other effects that are no longer needed should be disposed.
We do this by including a return function at the end of the useEffect Hook
import { useState, useEffect } from 'react';
import { createRoot } from 'react-dom/client';
function Timer() {
const [count, setCount] = useState(0);
useEffect(() => {
let timer = setTimeout(() => {
setCount((count) => count + 1);
}, 1000);
return () => clearTimeout(timer)
}, []);
return <h1>I've rendered {count} times!</h1>;
}
createRoot(document.getElementById('root')).render(
<Timer />
);
Note: To clear the timer, we had to name it.
Reference :https://www.w3schools.com/react/react_useeffect.asp





Top comments (1)
Good explanation