阅读 176

React state 更新原理(三) - state 快照的总结和实践

state 变量可能看起来像您可以读取和写入的常规 JavaScript 变量。但是,state 的行为更像是快照。设置它不会更改您已有的 state 变量,而是会触发重新渲染。

这个系列的文章你将学习到:

  • 如何设置 state 的触发器进行重新 render

  • state 何时以及如何更新

  • 设置 state 后为什么状态不会立即更新

  • 事件处理程序如何访问 state 的“快照”

系列文章

  • React state 更新原理 - render 时使用 state 的快照

  • React state 更新原理(二) - state 随时间的变化

总结

  • 设置 state 会进行新的 render。

  • React 将 state 存储在组件之外,就像在架子上一样。

  • 当您调用 useState 时,React 会为您提供这次 render 中 state 的快照。

  • 变量和事件处理程序在 re-render 时不会“幸存”。每次 render 都有自己的事件处理程序。

  • 每次 render(以及其中的函数)将始终“看到”React 赋予该 render 的 state 快照。

  • 你可以在心里替换事件处理程序中的 state,类似于你对 render 出的 JSX 的看法。

  • 过去创建的事件处理程序具有创建它们的时候 render 的 state 值。

实践 - 交通灯切换

学习完了这个系列的三篇文章,我们通过一个例子来加深印象吧~

这是一个人行横道灯组件,当按钮被按下时会切换:

import { useState } from 'react'; export default function TrafficLight() {   const [walk, setWalk] = useState(true);   function handleClick() {     setWalk(!walk);   }   return (     <>       <button onClick={handleClick}>         Change to {walk ? 'Stop' : 'Walk'}       </button>       <h1 style={{         color: walk ? 'darkgreen' : 'darkred'       }}>         {walk ? 'Walk' : 'Stop'}       </h1>     </>   ); } 复制代码

向单击处理程序添加 alert。当绿灯亮并显示“Walk,”时,点击按钮应该显示“Stop is next.”。当红灯亮并显示“Stop,”时,点击按钮应该显示“Walk is next.”。

把 alert 放在 setWalk调用之前还是之后有区别吗?

3

2

1

解决方式:

import { useState } from 'react'; export default function TrafficLight() {   const [walk, setWalk] = useState(true);   function handleClick() {     setWalk(!walk);     alert(walk ? 'Stop is next' : 'Walk is next');  // 这里   }   return (     <>       <button onClick={handleClick}>         Change to {walk ? 'Stop' : 'Walk'}       </button>       <h1 style={{         color: walk ? 'darkgreen' : 'darkred'       }}>         {walk ? 'Walk' : 'Stop'}       </h1>     </>   ); } 复制代码

把它放在 setWalk 调用之前还是之后都没有区别,这次 render 的 walk 值是固定的。调用 setWalk 只会在下一次 render 更改它,但不会影响上一次 render 的事件处理程序。

这行代码乍一看似乎有悖常理:

alert(walk ? 'Stop is next' : 'Walk is next'); 复制代码

但是如果你把它读成:“如果红绿灯显示‘Walk now’,那么消息应该是‘Stop is next’。”事件处理程序中的 walk 变量与 render 的 walk 值匹配并且不会改变。

您可以通过替换变量的方法来验证这是否正确。当 walktrue 时,你会得到:

<button onClick={() => {   setWalk(false);   alert('Stop is next'); }}>   Change to Stop </button> <h1 style={{color: 'darkgreen'}}>   Walk </h1> 复制代码

因此,单击“Change to Stop”会将 walk 设置为 false 的渲染进行排队,并 alert “Stop is next”。

 伪原创工具 SEO网站优化  https://www.237it.com/

作者:小十七_
链接:https://juejin.cn/post/7035501818989772836

文章分类
代码人生
版权声明:本站是系统测试站点,无实际运营。本文内容由互联网用户自发贡献,该文观点仅代表作者本人。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如发现本站有涉嫌抄袭侵权/违法违规的内容, 请发送邮件至 XXXXXXo@163.com 举报,一经查实,本站将立刻删除。
相关推荐