Warning: file_get_contents(/data/phpspider/zhask/data//catemap/9/javascript/471.json): failed to open stream: No such file or directory in /data/phpspider/zhask/libs/function.php on line 167

Warning: Invalid argument supplied for foreach() in /data/phpspider/zhask/libs/tag.function.php on line 1116

Notice: Undefined index: in /data/phpspider/zhask/libs/function.php on line 180

Warning: array_chunk() expects parameter 1 to be array, null given in /data/phpspider/zhask/libs/function.php on line 181
Javascript 在“与对象反应”中的子对象之间共享状态_Javascript_Reactjs_State - Fatal编程技术网

Javascript 在“与对象反应”中的子对象之间共享状态

Javascript 在“与对象反应”中的子对象之间共享状态,javascript,reactjs,state,Javascript,Reactjs,State,当我尝试从一个孩子更新所有孩子的状态时,我遇到了一些问题,下面是我的代码示例。其思想是自动更新其中一个组件的所有组件 我是react的新手,我才用了一个星期,所以可能这一切都是误会 从“React”导入React; 从'react dom'导入{render}; 从“./Hello”导入Hello; 类父类扩展了React.Component{ 建造师(道具){ 超级(道具); 此.state={ filedStr:“一些文本”, fieldObj:{ 字段1:是的, 字段2:正确 } } }

当我尝试从一个孩子更新所有孩子的状态时,我遇到了一些问题,下面是我的代码示例。其思想是自动更新其中一个组件的所有组件

我是react的新手,我才用了一个星期,所以可能这一切都是误会

从“React”导入React;
从'react dom'导入{render};
从“./Hello”导入Hello;
类父类扩展了React.Component{
建造师(道具){
超级(道具);
此.state={
filedStr:“一些文本”,
fieldObj:{
字段1:是的,
字段2:正确
}
}
}
updObj=(其中,val)=>{
this.setState(prevState=>({
fieldObj:{
…prevState.fieldObj,
[哪个]:瓦尔,
},
}));
};
render(){
返回(
父母亲
父组件状态中的值:{this.State.fieldObj.field1?1:0}:{this.State.fieldObj.field2?1:0}



) } } 子类扩展了React.Component{ 建造师(道具){ 超级(道具); 此.state={ obj:props.obj } } 更新=(其中)=>{ this.props.onUpdate(which,!this.state.obj[which]); this.setState(prevState=>({ obj:{ …prevState.obj, [which]:!prevState.obj[which], }, })); }; render(){ 返回( 小孩 子状态中的值:{this.State.obj.field1?1:0}:{this.State.obj.field2?1:0}
{this.update('field1')}>field1 {this.update('field2')}>field2 ) } } render(,document.getElementById('root'));
当所有子组件值都可以直接从道具派生时,您不需要在子组件中创建道具副本的状态并对其进行维护,您需要做的是直接修改父组件的状态,就像

import React from 'react';
import { render } from 'react-dom';
import Hello from './Hello';

class Parent extends React.Component {
  constructor(props) {
    super(props);

    this.state = {
      filedStr: 'some text',
      fieldObj: {
        field1: true,
        field2: true
      }
    }
  }

  updObj = (which, val) => {
    this.setState(prevState => ({
      fieldObj: {
        ...prevState.fieldObj,
        [which]: val,
      },
    }));
  };

  render() {
    return (
      <div>
        <h2>Parent</h2>
        Value in Parent Component State: {this.state.fieldObj.field1 ? 1 : 0} : {this.state.fieldObj.field2 ? 1 : 0}
        <br />
        <Child obj={this.state.fieldObj} onUpdate={this.updObj} />
        <br />
        <Child obj={this.state.fieldObj} onUpdate={this.updObj} />
        <br />
        <Child obj={this.state.fieldObj} onUpdate={this.updObj} />
      </div>
    )
  }
}

class Child extends React.Component {
  constructor(props) {
    super(props);

    this.state = {
      obj: props.obj
    }
  }

  update = (which) => {
    this.props.onUpdate(which, !this.props.obj[which]);
  };

  render() {
    return (
      <div>
        <h4>Child</h4>
        Value in Child State: {this.props.obj.field1 ? 1 : 0} : {this.props.obj.field2 ? 1 : 0}<br />
        <button type="button" onClick={(e) => { this.update('field1') }}>field1</button>
        <button type="button" onClick={(e) => { this.update('field2') }}>field2</button>
      </div>
    )
  }
}

render(<Parent />, document.getElementById('root'));
从“React”导入React;
从'react dom'导入{render};
从“./Hello”导入Hello;
类父类扩展了React.Component{
建造师(道具){
超级(道具);
此.state={
filedStr:“一些文本”,
fieldObj:{
字段1:是的,
字段2:正确
}
}
}
updObj=(其中,val)=>{
this.setState(prevState=>({
fieldObj:{
…prevState.fieldObj,
[哪个]:瓦尔,
},
}));
};
render(){
返回(
父母亲
父组件状态中的值:{this.State.fieldObj.field1?1:0}:{this.State.fieldObj.field2?1:0}



) } } 子类扩展了React.Component{ 建造师(道具){ 超级(道具); 此.state={ obj:props.obj } } 更新=(其中)=>{ this.props.onUpdate(which,!this.props.obj[which]); }; render(){ 返回( 小孩 子状态中的值:{this.props.obj.field1?1:0}:{this.props.obj.field2?1:0}
{this.update('field1')}>field1 {this.update('field2')}>field2 ) } } render(,document.getElementById('root'));


但是,如果您想知道为什么您的处理方式没有按预期工作,那是因为您没有根据父组件中的状态更新更新子组件的状态,您只在构造函数中设置了一次,而在组件装载时只调用了一次,您需要的是实现
组件willreceiveprops
生命周期功能

在这里,我更新了您的代码以满足您的需要-

您对子对象重新渲染的假设是错误的。当子级重新引发构造函数方法时,也就是说,构造函数只被调用一次。要使用下一个道具并更改状态,您需要使用渲染和组件WillReceiveProps。请参见react组件生命周期

问题是当您使用
onClick={(e)=>{this.update('field1')}}
onClick={(e)=>{this.update('field1')}}

您更新了父级的状态,此状态再次传递给子级。但是在孩子身上,你没有使用这种新道具。您使用的是状态,该状态仅在构造函数中更新,而在收到新道具后不会更新。(因为构造函数只被调用一次)

处理新道具的一种方法是直接在渲染中使用道具,因为组件将重新渲染,并且更新的道具将对其可用

另一种方法是,如果您希望使用状态,则更新componentWillReceiveProps中的状态。(我还想指出,强烈建议不要在componentWillReceiveProps和componentDidMount中执行setState)。所以最好使用第一步

componentWillReceiveProps(newProps) {
 if(newProps !== this.props){
  this.setState({newStateObjects})
 }
} 
componentWillReceiveProps(newProps) {
 if(newProps !== this.props){
  this.setState({newStateObjects})
 }
}