react中的setstate()
為我們提供了元件內的狀態管理方案,
本文將從component的角度來說明更合理的setstate()
在 react 文件的
state and lifecycle
一章中,明確的說明setstate()
的用法,向setstate()
中傳入乙個物件來對已有的 state 進行更新。
我們如果想要對這個 state 進行更新的話,就可以這樣使用setstate()
:
this.setstate();
你可能不知道的
最基本的用法世人皆知,但是,在 react 的文件下面,還寫著,處理關於非同步更新 state 的問題的時候,就不能簡單地傳入物件來進行更新了。這個時候,需要採用另外一種方式來對 state 進行更新。
setstate()
不僅能夠接受乙個物件作為引數,還能夠接受乙個函式作為引數。函式的引數即為 state 的前乙個狀態以及 props。
所以,我們可以向下面這樣來更新 state:
this.setstate((prevstate, props) => ());
這樣寫的話,能夠達到同樣的效果。那麼,他們之間有什麼區別呢?
區別為了能夠明確的看出 state 的更新,
採用乙個比較簡單的例子來進行說明。
設定乙個累加器,在 state 上設定乙個count
屬性,同時,為其增加乙個increment
方法,通過這個increment
方法來更新count
。
此處,採用給setstate()
傳入物件的方式來更新 state,同時,在此處設定每呼叫一次increment
方法的時候,就呼叫兩次setstate()
。具體的原因我在後文中會講解。
具體的**如下:
class
incrementbyobject
extends
react.component ;
this.increment = this.increment.bind(this);
} // 此處設定呼叫兩次 setstate()
increment() );
this.setstate();
} render() >incrementbyobjectbutton>
span>
div>
);}}
reactdom.render(
, document.getelementbyid('root')
);
這時候,點選 button 的時候,count
就會更新了。但是,可能與預期的有所差別。設定了點選一次就呼叫兩次setstate()
,但是,count
每一次卻還是只增加了 1,所以這是為什麼呢?
其實,在 react 內部,對於這種情況,採用的是物件合併的操作,就和我們所熟知的object.assign()
執行的結果一樣。
比如,我們有以下的**:
object.assign({}, , );
那麼,最終得到的結果將會是
。物件合併的操作,屬性值將會以最後設定的屬性的值為準,如果發現之前存在相同的屬性,那麼,這個屬性將會被後設定的屬性所替換。所以,也就不難理解為什麼呼叫了兩次setstate()
之後,count
依然只增加了 1 了。
用簡短的**說明就是這樣:
this.setstate();
// 同理於
object.assign({}, this.state, );
以上是採用物件的方式傳入setstate()
來更新 state 的說明。接下來再看看使用函式的方式來更新 state 會有怎麼樣的效果呢?
將上面的累加器採用另外的方式來實現一次,在setstate()
的時候,用傳入乙個函式的方式來更新 state。
class
incrementbyfunction
extends
react.component ;
this.increment = this.increment.bind(this);
} increment() ));
this.setstate((prevstate, props) => ());
} render() >incrementbyfunctionbutton>
span>
div>
);}}
reactdom.render(
, document.getelementbyid('root')
);
當再次點選按鈕的時候,就會發現,累加器就會每次增加 2 了。
可以通過檢視 react 的源**來找出這兩種更新 state 的區別 (此處只展示通過傳入函式進行更新的方式的部分原始碼)。
在 react 的源**中,可以看到這樣一句**:
this.updater.enqueuesetstate(this, partialstate, callback, 'setstate');
然後,enqueuesetstate
函式中又會有這樣的實現:
queue.push(partialstate);
enqueueupdate(internalinstance);
所以,與傳入物件更新 state 的方式不同,傳入函式來更新 state 的時候,react 會把更新 state 的函式加入到乙個佇列裡面,然後,按照函式的順序依次呼叫。同時,為每個函式傳入 state 的前乙個狀態,這樣,就能更合理的來更新 state 了。
問題所在
那麼,這就是傳入物件來更新 state 會導致的問題嗎?當然,這只是問題之一,還不是主要的問題。
之前也說過,在處理非同步更新的時候,需要用到傳入函式的方式來更新state。這樣,在更新下乙個 state 的時候,我們能夠正確的獲取到之前的 state,並在在其基礎之上進行相應的修改。而不是簡單地執行所謂的物件合併。
所以說,我們建議,在使用setstate
的時候,採用傳入函式來更新 state 的方式,這樣也是乙個更合理的方式。
setstate
PCB如何更合理的拼版
1 pcb拼板的外框 夾持邊 應採用閉環設計,確保pcb拼板固定在夾具上以後不會變形 2 pcb拼板寬度 260mm siemens線 或 300mm fuji線 如果需要自動點膠,pcb拼板寬度 長度 125 mm 180 mm 3 pcb拼板外形盡量接近正方形,推薦採用2 2 3 3 拼板 但不...
怎樣的工作量評估更合理?
如果你在外包公司工作過,或者你正在外包公司工作。我相信你一定會遇到評估專案工作量的情況,或者你是評估其中一部分的功能。在pmp裡面介紹,評估工作量最好是找最熟悉這個功能的人,也就是專家判斷。所以肯定非你莫屬了,畢竟你已經成為了專家。但我相信也肯定會遇到一種情況,工作量評估提交給客戶後,客戶開始砍工作...
linux c結構體更合理的初始化方法
教科書上講c語言結構體初始化是按照順序方式來講的,沒有涉及到亂序的方式。順序初始化struct必須要按照成員的順序進行,缺一不可,如果結構體比較大,很容易出現錯誤,而且表現形式不直觀,不能一眼看出各個struct各個資料成員的值。亂序初始化是c99標準新加的,比較直觀的一種初始化方式。相比順序初始化...