首页 > 其他分享 >为什么 Hooks,千万不要在 if 语句或者 for 循环语句中使用!

为什么 Hooks,千万不要在 if 语句或者 for 循环语句中使用!

时间:2024-02-25 14:35:46浏览次数:22  
标签:语句 调用 const Hooks 千万 React useState

如果组件中多次使用 useState 怎么办?React 如何“记住”哪个状态对应哪个变量?

React 是完全根据 useState 的调用顺序来“记住”状态归属的,假设组件代码如下:

const Counter = () => {
  const [count, setCount] = useState(0);
  const [foo, updateFoo] = useState('foo');
  
  ...
}

每一次 Counter 被渲染,都是第一次 useState 调用获得 count 和 setCount,
第二次 useState 调用获得 foo 和 updateFoo(这里我故意让命名不用 set 前缀,可见函数名可以随意)。

React 是渲染过程中的“上帝”,每一次渲染 Counter 都要由 React 发起,所以它有机会准备好一个内存记录,

当开始执行的时候,每一次 useState 调用对应内存记录上一个位置,而且是按照顺序来记录的。

React 不知道你把 useState 等 Hooks API 返回的结果赋值给什么变量,但是它也不需要知道,它只需要按照 useState 调用顺序记录就好了。

正因为这个原因,Hooks,千万不要在 if 语句或者 for 循环语句中使用!

像下面的代码,肯定会出乱子的:

const Counter = () => {
    const [count, setCount] = useState(0);
    if (count % 2 === 0) {
        const [foo, updateFoo] = useState('foo');
    }
    const [bar, updateBar] = useState('bar');
  ...
}

因为条件判断,让每次渲染中 useState 的调用次序不一致了,于是 React 就错乱了。

在React中,Hooks(如useStateuseEffect等)应当只在函数组件的顶层调用。这是因为React通过静态分析来确保Hooks的正确使用,它们必须按照自上而下的顺序被调用,并且不能在条件语句或循环体内调用。

以下是不推荐在条件语句或循环中使用Hooks的原因:

  1. 违反规则一致性

    • React Hooks的一个关键原则是每次渲染时都按照相同顺序执行。如果在if语句或者for循环里使用Hook,那么其执行顺序将变得不确定,这会打破React内部对Hook执行顺序的依赖和管理。
  2. 状态管理混乱

    • 如果允许在条件分支内创建状态,会导致组件状态逻辑难以理解和维护。每个状态都应该与组件的生命周期直接相关,而不是根据运行时条件临时创建。
  3. 潜在的问题与错误

    • 在条件语句或循环中使用Hook可能导致意外的行为,例如某些状态可能不会被正确地初始化或清理,造成内存泄漏等问题。
  4. 代码可读性和可维护性下降

    • 将Hook置于非顶层会使代码结构变得复杂,降低可读性。遵循统一的规则可以提高代码的一致性和团队协作效率。

因此,当需要根据条件决定是否使用某个Hook时,请考虑如何重构代码以保持Hook始终在函数组件的顶层调用。例如,可以通过合并条件分支共享的状态,或者在更高级别的抽象中处理条件判断。

标签:语句,调用,const,Hooks,千万,React,useState
From: https://www.cnblogs.com/longmo666/p/18032382

相关文章

  • 刘铁猛C#学习笔记9 表达式、语句2
    1.循环语句C#中有四种循环while循环,do-while循环,for计数循环,foreach遍历循环(1)while循环while()括号内写循环条件,一个bool类型表达式之后写一个嵌入式语句作为循环体 (2)do-while循环先执行一次,在判断循环条件,所以循环体至少会执行一次do{循环体}while(循环条件......
  • 刘铁猛C#学习笔记8 表达式、语句1
    表达式1.表达式的定义通用定义:一种专门用来求值的语法实体C#中定义:由一个或多个操作数,零个或多个操作符,功能是求值,求值的结果可能是四类Singlevalue、object、method、namespace(说明至少要有一个操作数,但不一定要有操作符)  C#中表达式值的类型:(1)单值Singlevalue......
  • sqlserver常用语句
    1、创建数据库MytestCREATEDATABASEMytest2、创建表StudentsCREATETABLEStudents(IDINTPRIMARYKEYIDENTITY(1,1),/*identity(1,1)为每次递增copy1位primarykey为主键*/NameVARCHAR(50)NNOTNULL,AgeINTNOTNULL,CityVARCHAR(50)NOTNULL......
  • day10- 条件语句
    Python代码如果不做其他处理,是自上往下执行的。但是在我们实际场景中,是需要做一些判断,所以用到了Python的条件判断语句可以根据不同的条件执行不同的代码块 包含if、elif、else关键字每句判断语句使用冒号:结尾,使用缩进划分语句块,相同缩进数的语句组成一个语句块。......
  • MySQL基础语句概括
    1.DDL语句(1)DDL数据库操作SHOWDATABASES;//显示当前数据库列表CREATEDATABASE数据库名;//创建数据库USE数据库名;//转到指定数据库SELECTDATABASE();//返回当前数据库名称(2)DDL表操作SHOWTABLES;CREATETABLE表名(字段......
  • 解密C语言选择结构:掌握条件语句与分支逻辑的利器
    ✨✨欢迎大家来到贝蒂大讲堂✨✨......
  • 4、ES查询语句
    批量索引文档如果你有大量文档要索引,你能通过批量API(bulkAPI)来批量提交它们。批量文档操作比单独提交请求显著更快,因为它极简了网络往返。最佳的批量数量取决于许多因素:文档的大小和复杂度、索引和搜索的负载以及集群可用资源。一种好的方式是批量处理1,000到5,000个文档......
  • Windows 批处理(bat) if条件判断语句使用教程
    基本描述在bat脚本中,if条件判断语句共有6种比较操作符,分别为其中,只有等于操作符可以使用符号“==”表示,其他操作符只能使用英文简写当参与比较的字符串是字符串时,将被转换为对于的ASCII码进行比较If指令基本格式指令格式为:if条件表达式(…)注意:英文缩写的比较操作符,左......
  • Oracle_SQL查询语句优化
     1.应尽量避免在where子句中使用!=或<>操作符,否则将引擎放弃使用索引而进行全表扫描。 2.对查询进行优化,应尽量避免全表扫描,首先应考虑在where及orderby涉及的列上建立索引。 3.应尽量避免在where子句中对字段进行null值判断,否则将导致引擎放弃使用索引而进行......
  • JavaSE的第七步 —— 开发者工具、控制语句、if单分支,if-esle双分支,if-else if-else多
    一、开发者工具工欲善其事,必先利其器。作为一个学习Java的小白,一个好的工具对我们的开发来说可以说是事半功倍。在网上看了很多大神们都推荐的使用IDEA开发工具,前30天可以免费使用。而在30天后大神提供了相应的解决方法,只要想学,办法总比困难多。加油每一个求学者。二、控制语句......