例如,我们有一个这样定义的状态,其中包含一些待办事项,如果要完成,我们想更改该待办事项的完成情况
[0]
为此,我们可以取消此操作。
this.state = {
// store an array of todo objects
todos: [
{ task: 'do the dishes', done: false, id: 1 },
{ task: 'vacuum the floor', done: true, id: 2 }
]
};
}
但是我有点困惑,数组上的find方法将向我们返回与其内部条件匹配的元素,然后将其存储在另一个变量中,然后进行访问以将其更改为true。 但是,我们仍然没有更改原始状态值,因为这是一个副本。
那我们怎么可以用它来保存它呢?
const theTodo = this.state.todos.find(t => t.id === id);
theTodo.done = true; // NOOOOO
this.setState({
todos: this.state.todos
});
答案 0 :(得分:2)
代码起作用的原因是因为State Updates are Merged。
调用
setState()
时, React将您提供的对象合并到当前状态。
但是,这只是不好的做法 You shouldn't mutate this.state
directly。
切勿直接突变
this.state
,因为事后致电setState()
可能会取代您所做的突变。将this.state
视为不变。
为完整起见,只需pass a function至this.setState
并使用map
保存不可变性规则。
通过更新功能可让您访问更新程序中的当前状态值。
this.setState((prevState) => {
const todos = prevState.todos.map((todo) =>
todo.id === id ? { ...todo, done: true } : todo
);
return { todos };
});
答案 1 :(得分:0)
只需spread一切
this.setState(oldState => {
const todos = oldState.todos;
const todoIndex = todos.findIndex(pr => pr.id === id);
const todo = todos[todoIndex];
const newTodos = [...todos.slice(0, todoIndex), {...todo, done: true}, ...todos.slice(todoIndex + 1)]
return {
...oldState,
todos
}
});
答案 2 :(得分:-1)
这不是问题,也不是与React框架有关的东西。这是对JavaScript的基本理解。当然,您将获得一个匹配项,find方法适用于任何数组,而您的 todo 是一个数组。 find方法返回一个新对象,而不是对其的引用。如果只想更新,请创建待办事项的副本,然后使用任何方法更新正确的待办事项,然后将复制的待办事项添加到新状态。您可以使用沉浸式运算符,也可以使用扩散运算符,可以通过多种方法进行。