简体   繁体   中英

Why the pop() or push() method of an array in the state of react can work

const { items } = this.state;
this.setState({ 
  items: this.state.items.slice(0, this.state.items.length - 1)
});

I know the code above can work well in react

However,

const { items } = this.state;
items.pop();
this.setState({ items });

I just don't know why this can still update the dom if there is a list rendered by the this.state.items (like <div className="list">{this.state.items}</div> ).

I am confused that the items.pop() have changed the origin state, isn't the next state's items equal the origin state's items.Why this can still update the dom .

The next state's items are not equal to the origin state's items because you are using an array mutable method (More info MDN Mutable Methods ). This pop method modify the array directly, it does not generate a copy like others methods ( map, filter no mutable methods).

Calling setState will always rerender the component. It doesnt matter if the state actually changed. To change that behaviour, you have to implement a custom shouldComponentUpdate .

If I understand you right, you are wondering why DOM changes if your mutation also applies the old state. You think "If I mutate the old one then both of the states points the same array's or object's reference". Yes, you are not creating a totally new array/object here but React does not look for the references I think.

React looks for many things but in your case, it looks for the DOM changes by diffing the elements, children of the array. Old DOM has one more element than the new DOM. Hence, it destroys the old one and mounts the new one.

You're using React.Component rather than React.PureComponent .

By default react will re-render on setState or if the parent re-renders even if the props or state didn't change. PureComponent however, does an equality check in shouldComponentUpdate , so that it won't re-render if all the props and state pass a strict equality check === (hence pure).

Is your question why the second code block updates your component even though the component state is not changing? Both code blocks you posted cause your component to update because you are callingsetState() . If you take a look at the documentation for setState() it says " setState() will always lead to a re-render unless shouldComponentUpdate() returns false " . If you don't want your component to update then don't call setState().

The technical post webpages of this site follow the CC BY-SA 4.0 protocol. If you need to reprint, please indicate the site URL or the original address.Any question please contact:yoyou2525@163.com.

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