Follow

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use
Contact

Why would a value get stale using closure in React?

In the documentation for useEffect() it shows the following example:

function Example() {
  const [count, setCount] = useState(0);

  useEffect(() => {
    document.title = `You clicked ${count} times`;
  });
}

It then says:

Experienced JavaScript developers might notice that the function
passed to useEffect is going to be different on every render. This is
intentional. In fact, this is what lets us read the count value from
inside the effect without worrying about it getting stale. Every time
we re-render, we schedule a different effect, replacing the previous
one.

MEDevel.com: Open-source for Healthcare and Education

Collecting and validating open-source software for healthcare, education, enterprise, development, medical imaging, medical records, and digital pathology.

Visit Medevel

I don’t understand why count would get stale inside useEffect() since useEffect has count within its closure. Since useEffect() is a hook, shouldn’t it always have access to the latest state variable? Also, in general, how can I be sure that I always have the latest value for a state variable?

>Solution :

I don’t understand why count would get stale inside useEffect() since useEffect has count within its closure.

Keep in mind that Example is going to be called multiple times, once for every render. So there are N renders, N count variables, and N useEffect functions. So it’s true that each effect function has count within its closure, but each of them has a specific count within its closure. Whatever value it had when the closure was created, that’s the value it will have when the effect runs. If you only created the function once, closing over the first value of count, then that code would only ever see the first value of count (ie, 0).

Also, in general, how can I be sure that I always have the latest value for a state variable?

If you’re setting state, then you can always access the latest value by using the function version of setState. For example:

setCount(prev => /* calculate new state from prev */)`

For other cases, either include the state in the dependency array of your useEffect, so that the effect re-runs when the count changes:

useEffect(() => {
  // some code that uses `count`
}, [count]);

Or leave the dependency array off entirely if you want the effect to run on every render.

useEffect(() => {
  // some code that uses `count`
});
Add a comment

Leave a Reply

Keep Up to Date with the Most Important News

By pressing the Subscribe button, you confirm that you have read and are agreeing to our Privacy Policy and Terms of Use

Discover more from Dev solutions

Subscribe now to keep reading and get access to the full archive.

Continue reading