首先聲明本人資質尚淺,本文只用於個人總結。如有錯誤,歡迎指正、共同提高。
-----------------------------------------------------------------------------------
其實想說的就是,state接收props對象的數據,涉及的值引用問題。
state和props建立賦值關系之后,state變動,對應props的內容也會跟着改變。
這樣再應付某些場景的時候,就需要做一些處理:
業務場景: 新舊數據對比
初期方案:
頁面初始化查詢時,將原始數據保存一份在頁面中的state中,然后頁面操作頁面中的state數據,props中的數據不變。
之后使用props原始數據,和state中改變后的數據進行比對,完成需求。
// 保存原始數據
例: recruits = { text:'1' };
let { recruits } = this.props.data;
this.setState({
inputList: recruits // 保存原始數據至state中
});
// 頁面操作,只修改state中的值
this.setState({
inputList: [{ text:'2'}]
});
// 結果
console.log(this.state.inputList.text);
// 2
console.log(this.props.recruits.text);
// 2
總結:
state接收的不是props的數據,而是props的數據引用地址,state修改props會隨之改變
問題解決方案( 其實就是值引用問題,涉及深淺copy ):
淺copy就不提了,這里使用的是深copy,但是深copy也是有區別的,就是copy數據的深度(數組or數組對象)
例: [{ text: '1' }, { text: '2' }];
深copy(假): 1、state數組長度變化時, 對應的props不會變動。 2、state數組中的對象變化時, 對應的props會變動
深copy(真): 1、state數組長度變化時,或者數組中的對象變化時, 對應的props都不會變動
let { recruits } = this.props.data;
let newRecruits = [];
if ( recruits && recruits.length>0 ) {
// 深copy (假)
// 1
// newRecruits = recruits.slice();
// 2
// newRecruits = [...recruits];
// 3
// newRecruits = recruits.concat();
// 深copy(真)
newRecruits = JSON.parse(JSON.stringify(recruits));
}
this.setState({
inputList: newRecruits
});