实际使用react hook的时候遇到的一些问题记录下来了,温故而知新。
例子1:界面上有个按钮,点击按钮界面上数值会增加1和2
const Test = () => {
const [arr, setArr] = useState([0]);
const handleClick = () => {
Promise.resolve()
.then(() => {
setArr([...arr, 1)];
}
.then(() => {
setArr([...arr, 2)];
}
}
return (
<div>
{arr.toString()}
<button onClick={handleClick}>按钮</button>
</div>
)
}
但是实际的结果是:
点击按钮,界面展示的是 0,2。跟预期需要展示的0,1,2不一样
例子2:点击按钮,执行三次setState,希望加3
const [count, setCount] = useState(0);
function handleClick() {
setCount(count + 1);
setCount(count + 1);
setCount(count + 1);
}
但是实际的结果是:
点击按钮,界面展示的是1。跟预期需要展示的3不一样
原因
组件内部的任何函数,包括事件处理函数和Effect,都是从它被创建的那次渲染中被看到的,所以引用的值都是旧的(没找到原文出处,所以对“看到”这个词表示疑惑),理解为:因为界面没有重新渲染,执行的函数作用域还是旧的,所以里面值的引用还是之前的,所以即使多次执行,拿到的都是旧值,会导致界面展示出现异常。
直接在handleClick里面打印count,展示的还是上一次的值,不是最新的值,这个由react的调度机制决定的。
修改建议:利用state hook参数可以是回调函数进行解决;或者可以用ref,但是ref记录值不太灵活,所以还是建议回调函数
setArr([...arr, 2)];
--------------变更成-------------
setArr((arr) => {
return [...arr, 2];
}