繁体   English   中英

如何通过引用而不是值传递父级的反应道具/状态?

How to pass react props/state of parent by reference, not value?

提示:本站收集StackOverFlow近2千万问答,支持中英文搜索,鼠标放在语句上弹窗显示对应的参考中文或英文, 本站还提供   中文繁体   英文版本   中英对照 版本,有任何建议请联系yoyou2525@163.com。

我正在使用反应钩子并尝试将父级的 state 传递给多个组件。 问题是当我想通过 state 的组件本身是 state 的一部分时。 我创建了一个示例来说明我的问题,我有一个按钮可以增加计数器并将另一个按钮附加到列表中。 我想查看显示的按钮列表,并且都从 state 读取相同的计数器值,但是当我 append 一个新按钮时,计数器的值总是在创建按钮时按值传递,它不更新。 在我的项目中(此处未显示),我通过将函数传递给组件以检索父 state 并手动更新所有组件来规避此问题,但是这样做我觉得我真的违反了不必要的反应的设计原则复杂的代码会导致更多的问题。

我的按钮示例:

import React from 'react'

function Button(props){
  return <button onClick={()=>{
    // increment the counter
    props.setcounter(cur=>cur+1);

    // add another button
    // these props are not passed by reference: how do I pass these by reference?
    props.setitems(items=>items.concat(<tr><td><Button {...props}/></td></tr>))
    }}>
    {props.counter}
    </button>
}
function App() {
  const [items,setitems]=React.useState([]);
  const [counter,setcounter]=React.useState(0);
  return (
    <div className="App">
      <table>
    <th><td>Button with props passed by reference:</td></th>
    <tr><td><Button counter={counter} setcounter={setcounter} setitems={setitems} /></td></tr>
      </table>
      <table>
       <th><td>Button with props passed by value:</td></th>
    {items}
      </table>
    </div>
  );
}

export default App;

 function Button(props){ return <button onClick={()=>{ // increment the counter props.setcounter(cur=>cur+1); // add another button // these props are not passed by reference: how do I pass these by reference? props.setitems(items=>items.concat(<tr><td><Button {...props}/></td></tr>)) }}> {props.counter} </button> } function App() { const [items,setitems]=React.useState([]); const [counter,setcounter]=React.useState(0); return ( <div className="App"> <table> <th><td>Button with props passed by reference:</td></th> <tr><td><Button counter={counter} setcounter={setcounter} setitems={setitems} /></td></tr> </table> <table> <th><td>Button with props passed by value:</td></th> {items} </table> </div> ); } ReactDOM.render( <App />, document.getElementById("root") );
 <script src="https://cdnjs.cloudflare.com/ajax/libs/react/16.8.4/umd/react.production.min.js"></script> <script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/16.8.4/umd/react-dom.production.min.js"></script> <div id="root"></div>

它能做什么:

在此处输入图像描述

当我多次单击顶部按钮时,它每次都会使用计数器的当前值创建一个新按钮,但它不会通过引用传递,因此不会在计数器值更新时更新。

我想要它做什么:

所有新创建的按钮都应该具有相同的计数器值,因为我希望它通过引用传递,而不是单击按钮时的值。 当我单击任何按钮时,应该创建一个新按钮,并且每个按钮上的值都应该更新以匹配新的计数器值。

1 个回复

问题是当我想通过 state 的组件本身是 state 的一部分时。

这确实是问题所在,并且正如您所发现的那样,React 中的反模式会产生陈旧的值。 理想情况下,您不应该在 state 中保留任何组件,如果您这样做,它们必须是完全纯净的(即在其生命周期内不会收到新的道具)。

当您调用此 state 设置器时实际发生了什么:

props.setitems(items=>items.concat(<tr><td><Button {...props}/></td></tr>))

这是吗,假设它是第一次被调用:

<Button counter={0} ... />

不仅该按钮的计数器只有值0 ,而且它创建的任何按钮都将具有相同的值。 你所说的在 React 上下文中实际上没有意义,因为整个要点是打破引用(以及更普遍的严格相等)以触发重新渲染和效果。

我们希望保持我们的 state 不可变,这意味着重新创建它的任何部分,这些部分在每次渲染时都会发生变化。 对于您正在做的工作,您必须通过在创建新按钮时循环与items长度一样多的次数来重新创建整个按钮存储。

您应该考虑的方式是如何数据中派生 UI,而不是将其存储数据:

 function Button(props){ return <button onClick={()=>{ props.setcounter(cur=>cur+1); props.setitems(items=> [...items, 1]) }}> {props.counter} </button> } function App() { const [items,setitems]=React.useState([1]); const [counter,setcounter]=React.useState(0); return ( <div className="App"> {items.map(() => <Button counter={counter} setcounter={setcounter} setitems={setitems}/>)} </div> ); } ReactDOM.render( <App />, document.getElementById("root") );
 <script src="https://cdnjs.cloudflare.com/ajax/libs/react/16.8.4/umd/react.production.min.js"></script> <script src="https://cdnjs.cloudflare.com/ajax/libs/react-dom/16.8.4/umd/react-dom.production.min.js"></script> <div id="root"></div>

2 如何将 state 传递给 React 中的道具

我是 React 的新手,并试图制作一个项目,该项目使用 disc.js 文件作为 MenuComponent.js 中的参数以在 DishdetailComponent.js 中使用。 但是,当我编译时,它没有给出任何错误或警告。 MenuComponent.js 是我的父级,而 Dishdet ...

5 如何在 React 中将 props props 从 Parent 传递给 this.props.children

我在尝试将道具传递给this.props.children遇到困难。 我知道有一些类似的帖子,但是,我相信我已经尝试了大多数公认的解决方案,但它仍然没有表现和预期。 所以,我想我错过了一些重要的东西。 总体思路是这样的:我有一个&lt;NavBar&gt;组件,我想将它包裹在我的页面上,如下所示。 ...

6 如何在 React 中将子道具存储到父 state?

我有一个Parent组件,它接收child和onSubmit道具。 孩子是具有任意道具的任意功能组件。 前任。 我想将孩子的道具存储在父组件中,以便孩子对自己的道具进行更改(通过使用自己的道具) 当单击提交按钮时,父母可以使用子道具将它们传递给提交 function。 我怎样才能做到这一点? ...

8 如何将道具传递到React组件中的状态

我已经创建了这个组件,该组件使用对象数组并填充位于状态中的结果。 这是一个轮播,根据存在的数据显示箭头,所以这就是我要通过状态执行此操作的原因。 (我包括了整个代码,所以您可以看到)。 现在,我希望将此轮播用于不同的页面,并希望动态地从每个页面提取数据。 我知道我可以通过道具来做到这 ...

9 将更新的父状态传递给子道具 React.js

我的父组件中有两个子组件,并设置了路由。 Child1 组件的按钮更新父组件的状态,我想将该状态的更新版本作为道具传递给 child2 组件。 问题是,虽然状态在父组件中明显更新(我检查了它),但它没有传递给 child2 组件(而是传递了旧版本的状态)。 我认为这是因为getdData函数(在父 ...

暂无
暂无

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2022 STACKOOM.COM