在設計React 組件的時候,必定要注意數據來源,確保每個數據都只有一個數據源。好比一個 state
不能既受 setState
的改變,又受 props
的變化而變化(好比componentWillReceiveProps
或是 getDerivedStateFromProps
中)。html
一旦遇到多數據來源的狀況,請將其按照如下方案進行從新設計。react
getDerivedStateFromProps
的做用:數組
state
只受到props
的影響;- 只有當
state
與prop
不一樣時,纔去修改state
;
受控組件是指 state 徹底受Prop控制的組件。一般,建議將組件設計成徹底受控組件。ide
const ControlComponent = (props) => {
reutrn (<div>{ props.name }</div>)
}
// 或者
class ControlComponent extends React.Component {
state = {
name: 'xxx'
}
// 使用了 getDerivedStateFromProps 類更新的state,最好不要在組件中再使用
// setState 來修改了,要保證數據來源的惟一性。
staric getDerivedStateFromProps(nextProps, preState) {
return {name: nextProps.name}
}
}
複製代碼
這個組件就是一個徹底受控組件,它沒有自身的狀態,徹底隨着props改變而改變。this
非受控組價是指組件存在 state,且state僅保存在這個組件內部,受組件內部的 setState
改變,不受 props
影響。spa
class NoncontrolComponent extends React.Component {
state = {
name: 'inside'
}
change = () => {
this.setState({name: 'newName'})
}
render() {
const { name } = this.state
return (<button onClick={this.change}>{name}</button>)
}
}
複製代碼
咱們知道key
是用來標識一個組件的。React
會根據 key
判斷數組中的哪些元素改變了,哪些元素被新增刪除了。若是數組中某個key消失了,React會認爲這個元素被刪除了,從而進行響應的操做。設計
因此根據這個特性,咱們能夠給一個非受控組件設置一個動態的 key
。當須要重置(?應該是從新構建)這個非受控組件的時候,咱們能夠直接改變 key
值就行了。code
這個key能夠是有意義的,也能夠是隨機生成的。component
若是不給非受控組件設置key,但仍想重置/改變組件,咱們能夠經過在組件中設置一個額外的標識符來達到相同的目的。htm
class NoncontrolComponent extends React.Component {
state = {
name: this.props.name,
id: this.props.id
}
static getDerivedStateFromProps(props, state) {
if (props.id !== state) {
return {
name: props.name,
id: props.id
}
}
return null // return null 表示不對 state 作改變
}
}
複製代碼
此外,咱們還能夠在組件中建立一個重置state
的的方法,而後讓父組件經過 ref
來調用該方法以達到改變組件狀態的目的。
class NoncontrolComponent extends React.Component {
state = {
name: 'xxx'
}
reset = name => {
this.setState({ name })
}
....
}
// 父組件使用 this.refs.component.reset() 就能夠改變組件狀態了
複製代碼