Is there a real disadvantage to modifying part of prevState and returning that part inside setState() ?
Example:
this.setState(prevState => {
prevState.myObject.isItTrue = !prevState.myObject.isItTrue;
return {myObject: prevState.myObject};
});
Rather than:
this.setState(prevState => {
const myObject = Object.assign({}, prevState.myObject);
myObject.isItTrue = !myObject.isItTrue;
return {myObject: myObject};
});
Is there any real disadvantage to the first code where I save myself the Object.assign()
?
EDIT: If I am correct, prevState.myObject is simply a reference to this.state.myObject, so changing prevState.myObject actually changes this.myObject.object as well! However, this doesn't seem to break anything, as long as I use setState() to pass an object that contains the new data, even if it's just a reference to the old objects inside this.state. Do you agree that this is still ok, i.e. it won't break anything to do it like this?
Following documentation:
state is a reference to the component state at the time the change is being applied. It should not be directly mutated. Instead, changes should be represented by building a new object based on the input from state and props.
https://reactjs.org/docs/react-component.html
So you should not apply changes directly to that state.
Either way, why not do something like this?:
this.setState(prevState => ({
myObject : {
...prevState.myObject,
isItTrue: !prevState.myObject.isItTrue,
}
}));
This way will get all the elements from the prevState but also change all the ones you want to modify.
First prevState
and the this.state
are the same object. So you are modifying the actual state directly.
Secondly, down the road you might pass the myObject
as a prop to another component, and since it will be the same object always that component will not know that something has changed and it will not re-render (for example PureComponent
and ones that implement componentDidUpdate
or shouldComponentUpdate
and test for changes)
See https://codesandbox.io/s/zen-aryabhata-m07l4 for showcases of all issues.
So you should use
this.setState(state => ({
myObject: {
...state.myObject,
isItTrue: !state.myObject.isItTrue
}
}));
If you love us? You can donate to us via Paypal or buy me a coffee so we can maintain and grow! Thank you!
Donate Us With