React有一个特点就是数据不可变,当这个数据改变时他不会真正改变这个数据的值,而是再生成一个对象
做一个+1的案例
使用this.state.n+=1后页面的数据不会刷新,因为没有只不过时UI没有更新this.state.n+=1;应该使用this.setState({ n: this.state.n + 1 })生成一个新的对象,调用setState才会触发跟新
class Son extends React.Component{
//类组件的数据初始化,super()必须要写否则报错
constructor(){
super()
this.state={
n:0
};
};
add(){
// this.state.n+=1
this.setState({ n: this.state.n + 1 });
console.log(this.state.n) //0
};
此时打印出的是0,因为要等这个方法全部完成之后新的值才会覆盖原先的值,setState是一个异步方法,不会马上去修改state
类组件自动合并,函数组件不会自动合并
setState会自动合并第一层属性,但是不会自动合并第二层
此时的n和m是第一层属性;只改变一个n的值,另一个m如果没有修改就不会改变,m按原样不变
class Son extends React.Component{
constructor(){
super()
this.state={
n:0
m:0
};
};
add(){
this.setState({
(state)=>{
const n = state.n+1
return {n:n}
}
})
};
添加一个user对象,user对象里的属性就属于第二层属性
此时只改变第二层属性里的name,age不变,但是最后结果age会被置空(age丢失),age会变成undefined
class Son extends React.Component{
constructor(){
super()
this.state={
n:0,
m:0,
user:{
name:dong,
age:18
}
};
};
changeUser(){
this.setState({
user:{
name:"jack"
}
})
};
解决方法
解决方法是使用扩展运算符先将原先的属性复制过来,再改其中的属性
changeUser(){
this.setState({
user:{
...this.state.user,
name:"jack"
}
})
//或者这样写,会把this.state.user拷贝到{}这个新对象上边,然后新对象再赋值给user
const user = Object.assign({},this.state.user);