【问题标题】:Why is the alert showing the previous state in this code? [duplicate]为什么警报显示此代码中的先前状态? [复制]
【发布时间】:2019-11-29 19:27:47
【问题描述】:

当我增加时,警报会给出真正的 numRef.current 值,但 stateNumber 的值始终是前一个。

我知道这是由于闭包造成的,但即使我一直在阅读有关范围和闭包如何工作的内容,我也不明白为什么在这种情况下 stateNumber 的值不是当前值,因为 setStateNumber 被调用在 setTimeout 之前,所以值应该已经更新了

import React, { useState, useEffect, useRef } from "react";

const RefComponent = () => {
  const [stateNumber, setStateNumber] = useState(0);
  const numRef = useRef(0);

  function incrementAndDelayLogging() {
    setStateNumber(stateNumber + 1);
    numRef.current++;
    setTimeout(
      () => alert(`state: ${stateNumber} | ref: ${numRef.current}`),
      1000
    );
  }

  return (
    <div>
      <h1>useRef Example</h1>
      <button onClick={incrementAndDelayLogging}>delay logging</button>
      <h4>state: {stateNumber}</h4>
      <h4>ref: {numRef.current}</h4>
    </div>
  );
};

export default RefComponent;

【问题讨论】:

  • set 是异步的.. 你应该尝试将你的值记录在 useEffect 这与 componentDidUpdate 等价
  • 这是因为当警报触发时反应状态是异步更新的,它会记住其先前的状态(因为它是异步的)并且警报具有前一个的范围。所以它打印前一个

标签: javascript reactjs closures react-hooks


【解决方案1】:
function incrementAndDelayLogging() {
const newStateNumber = stateNumber + 1
setStateNumber(newStateNumber);
numRef.current++;
setTimeout(
  () => alert(`state: ${newStateNumber} | ref: ${numRef.current}`),
  1000
);

}

这可能会解决它:)

【讨论】:

    猜你喜欢
    • 2011-01-27
    • 2011-10-17
    • 1970-01-01
    • 2016-08-03
    • 1970-01-01
    • 2019-01-11
    • 1970-01-01
    • 2017-03-06
    • 1970-01-01
    相关资源
    最近更新 更多