简体   繁体   English

如何使用setState更新对象数组中的对象

[英]How to update an object in an array of Objects using setState

I am using React, my state is defined as an array of object. 我正在使用React,我的状态被定义为一个对象数组。 I need to be able to change only one specific element in the state.data array, example object with id 1. 我需要能够只更改state.data数组中的一个特定元素,id为1的示例对象。

I would like to know: 我想知道:

  • what is the proper way how to use setState() in this scenario. 在这种情况下如何使用setState()的正确方法是什么。

 constructor(props) { super(props); this.state = { data: [{ id: 0, title: 'Buy a', status: 0, // 0 = todo, 1 = done }, { id: 1, title: 'Buy b', status: 0, }, { id: 2, title: 'Buy c', status: 0, } ] }; this.onTitleChange = this.onTitleChange.bind(this); } onTitleChange(id, title) { console.log(id, title); debugger } 

You can get do a cloning of the state object using spread operator and then find the index of object in array with a given id using findIndex method Modify the object and set the state. 您可以使用spread运算符克隆状态对象,然后使用findIndex方法在给定id的数组中查找对象的索引修改对象并设置状态。

constructor(props) {
  super(props);
  this.state = {
    data: [{
        id: 0,
        title: 'Buy a',
        status: 0, // 0 = todo, 1 = done
      },
      {
        id: 1,
        title: 'Buy b',
        status: 0,
      },
      {
        id: 2,
        title: 'Buy c',
        status: 0,
      }
    ]
  };
  this.onTitleChange = this.onTitleChange.bind(this);
}
onTitleChange(id, title) {
   var data = [...this.state.data];
   var index = data.findIndex(obj => obj.id === id);
   data[index].title = title;
   this.setState({data});
}

You could also do something like this: 你也可以这样做:

onChange = (id, value, field) => { 
    this.setState((prevState) => ({
            data: prevState.data.map((d, index) => { //d = object, index = index in array
                if (d.id === id) {
                    return {
                        ...d,
                        [field]: value //field/name in object
                    }
                }
                return d
            })
        }), () => {
            console.log("New value of", field, "=", value, "in object with id", id);
        });
}

You can also modify the way you are 您也可以修改自己的方式

storing the state in the below format 以下面的格式存储状态

for ease, hope this helps! 为了方便,希望这有帮助!

constructor(props) {
  super(props);
  this.state = {
    data: [
     0: {
        id: 0,
        title: 'Buy a',
        status: 0, // 0 = todo, 1 = done
      },
     1: {
        id: 1,
        title: 'Buy b',
        status: 0,
      },
     2: {
        id: 2,
        title: 'Buy c',
        status: 0,
      }
    ]
  };
  this.onTitleChange = this.onTitleChange.bind(this);
}

onTitleChange(id, title) {
   var newData = [...this.state.data];
   newData[id].title = title;
   this.setState({newData});
}

A simple solution would be: 一个简单的解决方案是:

const idx = this.state.data.findIndex(obj => obj === id);
this.state.data[idx].title = title;

For more complex component, I would recommend to use Immutable.js List 对于更复杂的组件,我建议使用Immutable.js List

I would use the spread operator to update the state. 我会使用spread运算符来更新状态。

onTitleChange(id, title) {
  const { data } = this.state
  const index = data.findIndex(d => d.id === id)

  this.setState({
    data: [
      ...data.slice(0, index),
      {
        ...data[index],
        title: title,
      },
      ...data.slice(index + 1)
    ]
  })
}

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

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