为什么不能在循环或嵌套函数内调用 React Hooks? [英] Why can't React Hooks be called inside loops or nested function?

查看:52
本文介绍了为什么不能在循环或嵌套函数内调用 React Hooks?的处理方法,对大家解决问题具有一定的参考价值,需要的朋友们下面随着小编来一起学习吧!

问题描述

React Hooks 文档不要在循环、条件或嵌套函数中调用 Hook.

我知道执行顺序很重要,这样 React 才能知道哪个状态对应于哪个 useState 调用.鉴于此,很明显不能在条件内调用钩子.

但是如果我们在迭代次数不随时间变化的循环中调用 useState ,我看不出有什么问题.这是一个例子:

const App = () =>{常量输入 = [];for(让我= 0;我<10;我++){输入[i] = useState('name' + i);}return input.map(([value, setValue], index) => (<div key={index}><输入值={value} onChange={e =>setValue(e.target.value)}/>

));}导出默认应用程序;

上面这段代码有问题吗?如果在每次渲染时都调用此函数,那么在嵌套函数中调用 useState 有什么问题?

解决方案

参考 说明了实际原因,

<块引用>

通过遵循此规则,您可以确保每次渲染组件时都以相同的顺序调用 Hook.这就是允许 React 在多个 useState 和 useEffect 调用之间正确保留 Hooks 状态的原因.

并提供示例,说明为什么这很重要.

循环、条件和嵌套函数是可能扰乱钩子执行顺序的常见地方.如果开发人员确定循环等是合理的并保证顺序,那么就没有问题.

事实上,如果循环被提取为有效的自定义钩子一个函数,可以在需要时禁用 linter 规则(演示):

//eslint-disable-next-line react-hooks/rules-of-hooksconst useInputs = n =>[...Array(n)].map((_, i) => useState('name' + i));

上面的例子不会导致问题,但循环不一定是合理的;它可以是单个数组状态:

const App = () =>{const [inputs, setInputs] = useState(Array(10).fill(''));const setInput = (i, v) =>{setInputs(Object.assign([...inputs], { [i]: v }));};return input.map((v, i) => (<div key={i}><输入值={v} onChange={e =>setInput(i, e.target.value)}/>

));}

React Hooks documentation says to not call Hooks inside loops, conditions, or nested functions.

I understood that the order of execution was important so React can know which state corresponds to which useState call. Given that, it's obvious that a hook cannot be called inside a condition.

But I don't see what is the problem if we call useState inside a loop where the number of iterations doen't change over the time. Here is an example :

const App = () => {
  const inputs = [];

  for(let i = 0; i < 10; i++) {
    inputs[i] = useState('name' + i);
  }

  return inputs.map(([value, setValue], index) => (
    <div key={index}> 
      <input value={value} onChange={e => setValue(e.target.value)} />
    </div>
  ));
}

export default App;

Is there a problem with this code above ? And what is the problem of calling useState inside a nested function, if this function is called on every render ?

解决方案

The reference states the actual cause,

By following this rule, you ensure that Hooks are called in the same order each time a component renders. That’s what allows React to correctly preserve the state of Hooks between multiple useState and useEffect calls.

and provides the example that shows why this is important.

Loops, conditions and nested functions are common places where the order in which hooks are executed may be disturbed. If a developer is sure that a loop, etc. is justified and guarantees the order then there's no problem.

In fact, a loop would be considered valid custom hook if it was extracted to a function, a linter rule can be disabled where needed (a demo):

// eslint-disable-next-line react-hooks/rules-of-hooks
const useInputs = n => [...Array(n)].map((_, i) => useState('name' + i));

The example above won't cause problems but a loop isn't necessarily justified; it can be a single array state:

const App = () => {
  const [inputs, setInputs] = useState(Array(10).fill(''));
  const setInput = (i, v) => {
    setInputs(Object.assign([...inputs], { [i]: v }));
  };

  return inputs.map((v, i) => (
    <div key={i}> 
      <input value={v} onChange={e => setInput(i, e.target.value)} />
    </div>
  ));
}

这篇关于为什么不能在循环或嵌套函数内调用 React Hooks?的文章就介绍到这了,希望我们推荐的答案对大家有所帮助,也希望大家多多支持IT屋!

查看全文
相关文章
前端开发最新文章
热门教程
热门工具
登录 关闭
扫码关注1秒登录
发送“验证码”获取 | 15天全站免登陆