title: React's state update vs ref async update
body: <p>React's state update is <strong>async</strong> and that's why you should not try to use the <strong>state</strong> (like <strong>logging</strong> or <strong>any other reading operation</strong>) just after setting it. But only <strong>async</strong> keyword seems to not give the total picture of how React updates the state.</p>
  <p>How is this <strong>state</strong> update different from a <strong>ref</strong> update done asynchronously ?</p>
  <p>Consider the following snippet where we simulate <strong>async</strong> updation of <code>statefulRef</code>. Even after we update the <code>statefulRef</code> <strong>asynchronously</strong>, if we access it after the update, we will get the latest value. But the same is not true with <code>state</code>. I know that both <strong>render</strong> and <strong>closure</strong> take part in explaining this <code>state</code> update but I would like to have a detailed answer explaining the differences of <strong>async</strong> behavior that we see below :-</p>
  <p><div class="snippet" data-lang="js" data-hide="false" data-console="true" data-babel="true">
  <div class="snippet-code">
  <pre class="snippet-code-js lang-js prettyprint-override"><code>const {
    useState,
    useRef
  } = React
  
  function App() {
    const [state, setState] = useState({current:0});
    const statefulRef = useRef(0);
  
    function updateState() {
      // below is async operation
      setState({current:state.current + 1});
      // below is async logging
      setTimeout(() =&gt; console.log("React state : ",state.current), 500);
    }
  
    function updateRef() {
      // below is async operation
      setTimeout(() =&gt; statefulRef.current += 1, 200);
      // below is async logging
      setTimeout(() =&gt; console.log("React ref : ",statefulRef.current), 500);
    }
  
    return ( 
      &lt;div &gt;
      &lt;button onClick = {updateState}&gt; Update State &lt;/button&gt; 
      &lt;button onClick = {updateRef}&gt; Update Ref &lt;/button&gt; 
      &lt;/div&gt;
    )
  
  }
  
  ReactDOM.render( &lt; App / &gt; , document.getElementById("root"));</code></pre>
  <pre class="snippet-code-html lang-html prettyprint-override"><code>&lt;script src="https://cdnjs.cloudflare.com/ajax/libs/react/17.0.1/umd/react.production.min.js"&gt;&lt;/script&gt;
  &lt;script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/17.0.1/umd/react-dom.production.min.js"&gt;&lt;/script&gt;
  &lt;div id="root"&gt;&lt;/div&gt;</code></pre>
  </div>
  </div>
  </p>