const Parent = () => {
let [hitCounter,setHitCounter] = React.useState(0);
let [clickCounter,setClickCounter] = React.useState(0);
const data= React.useMemo(() => {
console.log("in useMemo")
return hitCounter
},[hitCounter]);
return(
<>
<Child hitCounter={data}/>
<input type="button" onClick={() => setHitCounter(hitCounter + 1)} value="Hit me"/>
{hitCounter}
<div><input type="button" onClick={() => setClickCounter(clickCounter + 1)} value="Click me"/>
{clickCounter}</div>
</>
)
}
export default Parent;
const Child = (props) => {
let data = 0;
useEffect(() => {
console.log("in useeffect");
data = props.counter;
},[props.counter])
console.log("in Child");
return(
<div>
The Hit counter value is {data}
</div>
)
}
export default Child
In the Parent component, I have 2 buttons Hit me and Click me. On click of each of them the respective counter gets incremented. So when I am clicking on 'Click me' the clickCounter gets incremented but hitCounter remains same. I am sending the memoized 'Hit me' count(hitCounter) to the child.
My confusion is why the child component is still getting re-rendered when clickCounter changes even though I am not passing it to child and have used useMemo for hitcounter(this is not getting changed).
I am using useMemo for hitcounter to make sure the child does not gets re-rendered when hitcounter is not changing.
In response to a change in state, React will re-render that component with the changed state, and all children of that component. The props you pass to those children do not matter.
Consider this example:
Here every time you click the button,
'foo'will get logged to the console. Here theAppcomponent has updated state, so all it's children render, too.If you don't want that, you can use React.memo on the component, not the state.
This is not a hook, it's a wrapper around component declarations.
With that change, the
Childcomponent will only render once for it's lifetime since it props could never change.See Stackblitz
That said, you rarely need to do this. You should only be looking at this if yo are having actual performance problems in your app. And even if you are, in my experience it's usually more due to your business logic than react's rendering performance.