React?Hook之使用State?Hook的方法
Hook 簡(jiǎn)介章節(jié)中使用下面的例子介紹了 Hook:
import React, { useState, useEffect } from 'react'; function Example() { const [count, setCount] = useState(0); // Similar to componentDidMount and componentDidUpdate: useEffect(() => { // Update the document title using the browser API document.title = `You clicked ${count} times`; }); return ( <div> <p>You clicked {count} times</p> <button onClick={() => setCount(count + 1)}> Click me </button> </div> ); }
我們將通過(guò)將這段代碼與一個(gè)等價(jià)的 class
示例進(jìn)行比較來(lái)開始學(xué)習(xí) Hook。
等價(jià)的 class 示例
如果你之前在 React 中使用過(guò) class
,這段代碼看起來(lái)應(yīng)該很熟悉:
class Example extends React.Component { constructor(props) { super(props); this.state = { count: 0 }; } render() { return ( <div> <p>You clicked {this.state.count} times</p> <button onClick={() => this.setState({ count: this.state.count + 1 })}> Click me </button> </div> ); } }
state
初始值為 { count: 0 }
,當(dāng)用戶點(diǎn)擊按鈕后,我們通過(guò)調(diào)用 this.setState()
來(lái)增加 state.count
。整個(gè)章節(jié)中都將使用該 class
的代碼片段做示例。
Hook 和函數(shù)組件
復(fù)習(xí)一下, React 的函數(shù)組件是這樣的:
const Example = (props) => { // 你可以在這使用 Hook return <div />; }
或是這樣:
function Example(props) { // 你可以在這使用 Hook return <div />; }
你之前可能把它們叫做“無(wú)狀態(tài)組件”。但現(xiàn)在我們?yōu)樗鼈円肓耸褂?React state
的能力,所以我們更喜歡叫它”函數(shù)組件”。
Hook 在 class
內(nèi)部是不起作用的。但你可以使用它們來(lái)取代 class
。
Hook 是什么?
在新示例中,首先引入 React 中 useState
的 Hook
import React, { useState } from 'react'; function Example() { // ... }
- Hook 是什么? Hook 是一個(gè)特殊的函數(shù),它可以讓你“鉤入” React 的特性。例如,
useState
是允許你在 React 函數(shù)組件中添加state
的 Hook。稍后我們將學(xué)習(xí)其他 Hook。 - 什么時(shí)候我會(huì)用 Hook? 如果你在編寫函數(shù)組件并意識(shí)到需要向其添加一些
state
,以前的做法是必須將其轉(zhuǎn)化為class
?,F(xiàn)在你可以在現(xiàn)有的函數(shù)組件中使用 Hook。
聲明 State 變量
在 class
中,我們通過(guò)在構(gòu)造函數(shù)中設(shè)置 this.state
為 { count: 0 }
來(lái)初始化 count state
為 0
:
class Example extends React.Component { constructor(props) { super(props); this.state = { count: 0 }; }
在函數(shù)組件中,我們沒(méi)有 this
,所以我們不能分配或讀取 this.state
。我們直接在組件中調(diào)用 useState
Hook:
import React, { useState } from 'react'; function Example() { // 聲明一個(gè)叫 “count” 的 state 變量 const [count, setCount] = useState(0);
- 調(diào)用 useState 方法的時(shí)候做了什么? 它定義一個(gè) “
state
變量”。我們的變量叫count
, 但是我們可以叫他任何名字,比如banana
。這是一種在函數(shù)調(diào)用時(shí)保存變量的方式 ——useState
是一種新方法,它與class
里面的this.state
提供的功能完全相同。一般來(lái)說(shuō),在函數(shù)退出后變量就會(huì)”消失”,而state
中的變量會(huì)被 React 保留。 - useState 需要哪些參數(shù)?
useState()
方法里面唯一的參數(shù)就是初始state
。不同于class
的是,我們可以按照需要使用數(shù)字或字符串對(duì)其進(jìn)行賦值,而不一定是對(duì)象。在示例中,只需使用數(shù)字來(lái)記錄用戶點(diǎn)擊次數(shù),所以我們傳了0
作為變量的初始state
。(如果我們想要在state
中存儲(chǔ)兩個(gè)不同的變量,只需調(diào)用useState()
兩次即可。) - useState 方法的返回值是什么? 返回值為:當(dāng)前
state
以及更新state
的函數(shù)。這就是我們寫const [count, setCount] = useState()
的原因。這與class
里面this.state.count
和this.setState
類似,唯一區(qū)別就是你需要成對(duì)的獲取它們。如果你不熟悉我們使用的語(yǔ)法,我們會(huì)在本章節(jié)的底部介紹它。
既然我們知道了 useState
的作用,我們的示例應(yīng)該更容易理解了:
import React, { useState } from 'react'; function Example() { // 聲明一個(gè)叫 "count" 的 state 變量 const [count, setCount] = useState(0);
我們聲明了一個(gè)叫 count
的 state
變量,然后把它設(shè)為 0
。React 會(huì)在重復(fù)渲染時(shí)記住它當(dāng)前的值,并且提供最新的值給我們的函數(shù)。我們可以通過(guò)調(diào)用 setCount
來(lái)更新當(dāng)前的 count
。
注意
你可能想知道:為什么叫
useState
而不叫createState
?“Create” 可能不是很準(zhǔn)確,因?yàn)?nbsp;
state
只在組件首次渲染的時(shí)候被創(chuàng)建。在下一次重新渲染時(shí),useState
返回給我們當(dāng)前的state
。否則它就不是state
了!這也是 Hook 的名字總是以use
開頭的一個(gè)原因。我們將在后面的 Hook 規(guī)則中了解原因。
讀取 State
當(dāng)我們想在 class
中顯示當(dāng)前的 count
,我們讀取 this.state.count
:
<p>You clicked {this.state.count} times</p>
在函數(shù)中,我們可以直接用 count
:
<p>You clicked {count} times</p>
更新 State
在 class
中,我們需要調(diào)用 this.setState()
來(lái)更新 count
值:
<button onClick={() => this.setState({ count: this.state.count + 1 })}> Click me </button>
在函數(shù)中,我們已經(jīng)有了 setCount
和 count
變量,所以我們不需要 this
:
<button onClick={() => setCount(count + 1)}> Click me </button>
小結(jié)
現(xiàn)在讓我們來(lái)仔細(xì)回顧一下學(xué)到的知識(shí),看下我們是否真正理解了。
import React, { useState } from 'react'; function Example() { const [count, setCount] = useState(0); return ( <div> <p>You clicked {count} times</p> <button onClick={() => setCount(count + 1)}> Click me </button> </div> ); }
- 第一行 - 引入React 中的
useState
Hook。它讓我們?cè)诤瘮?shù)組件中存儲(chǔ)內(nèi)部state
。 - 第四行 - 在
Example
組件內(nèi)部,我們通過(guò)調(diào)用useState
Hook 聲明了一個(gè)新的state
變量。它返回一對(duì)值給到我們命名的變量上。我們把變量命名為count
,因?yàn)樗鎯?chǔ)的是點(diǎn)擊次數(shù)。我們通過(guò)傳0
作為useState
唯一的參數(shù)來(lái)將其初始化為0
。第二個(gè)返回的值本身就是一個(gè)函數(shù)。它讓我們可以更新count
的值,所以我們叫它setCount
。 - 第九行 - 當(dāng)用戶點(diǎn)擊按鈕后,我們傳遞一個(gè)新的值給
setCount
。React 會(huì)重新渲染Example
組件,并把最新的count
傳給它。
提示:方括號(hào)有什么用?
你可能注意到我們用方括號(hào)定義了一個(gè) state
變量
const [count, setCount] = useState(0);
等號(hào)左邊名字并不是 React API 的部分,你可以自己取名字:
const [fruit, setFruit] = useState('banana');
這種 JavaScript 語(yǔ)法叫數(shù)組解構(gòu)。它意味著我們同時(shí)創(chuàng)建了 fruit
和 setFruit
兩個(gè)變量,fruit
的值為 useState
返回的第一個(gè)值,setFruit
是返回的第二個(gè)值。它等價(jià)于下面的代碼:
var fruitStateVariable = useState('banana'); // 返回一個(gè)有兩個(gè)元素的數(shù)組 var fruit = fruitStateVariable[0]; // 數(shù)組里的第一個(gè)值 var setFruit = fruitStateVariable[1]; // 數(shù)組里的第二個(gè)值
當(dāng)我們使用 useState
定義 state
變量時(shí)候,它返回一個(gè)有兩個(gè)值的數(shù)組。第一個(gè)值是當(dāng)前的 state
,第二個(gè)值是更新 state
的函數(shù)。使用 [0]
和 [1]
來(lái)訪問(wèn)有點(diǎn)令人困惑,因?yàn)樗鼈冇刑囟ǖ暮x。這就是我們使用數(shù)組解構(gòu)的原因。
提示:使用多個(gè) state 變量
將 state
變量聲明為一對(duì) [something, setSomething]
也很方便,因?yàn)槿绻覀兿胧褂枚鄠€(gè) state
變量,它允許我們給不同的 state
變量取不同的名稱:
function ExampleWithManyStates() { // 聲明多個(gè) state 變量 const [age, setAge] = useState(42); const [fruit, setFruit] = useState('banana'); const [todos, setTodos] = useState([{ text: '學(xué)習(xí) Hook' }]);
在以上組件中,我們有局部變量 age
,fruit
和 todos
,并且我們可以單獨(dú)更新它們:
function handleOrangeClick() { // 和 this.setState({ fruit: 'orange' }) 類似 setFruit('orange'); }
你不必使用多個(gè) state
變量。State
變量可以很好地存儲(chǔ)對(duì)象和數(shù)組,因此,你仍然可以將相關(guān)數(shù)據(jù)分為一組。然而,不像 class
中的 this.setState
,更新 state
變量總是替換它而不是合并它。
總結(jié)
本篇文章就到這里了,希望能夠給你帶來(lái)幫助,也希望您能夠多多關(guān)注腳本之家的更多內(nèi)容!
相關(guān)文章
react進(jìn)階教程之異常處理機(jī)制error?Boundaries
在react中一旦出錯(cuò),如果每個(gè)組件去處理出錯(cuò)情況則比較麻煩,下面這篇文章主要給大家介紹了關(guān)于react進(jìn)階教程之異常處理機(jī)制error?Boundaries的相關(guān)資料,文中通過(guò)實(shí)例代碼介紹的非常詳細(xì),需要的朋友可以參考下2022-08-08Ant Design與Ant Design pro入門使用教程
Ant Design 是一個(gè)服務(wù)于企業(yè)級(jí)產(chǎn)品的設(shè)計(jì)體系,組件庫(kù)是它的 React 實(shí)現(xiàn),antd 被發(fā)布為一個(gè) npm 包方便開發(fā)者安裝并使用,這篇文章主要介紹了Ant Design與Ant Design pro入門,需要的朋友可以參考下2023-12-12淺談React的React.FC與React.Component的使用
本文主要介紹了React的React.FC與React.Component的使用,文中通過(guò)示例代碼介紹的非常詳細(xì),具有一定的參考價(jià)值,感興趣的小伙伴們可以參考一下2021-09-09TypeScript在React項(xiàng)目中的使用實(shí)踐總結(jié)
這篇文章主要介紹了TypeScript在React項(xiàng)目中的使用總結(jié),本文給大家介紹的非常詳細(xì),對(duì)大家的學(xué)習(xí)或工作具有一定的參考借鑒價(jià)值,需要的朋友可以參考下2021-04-04詳解一個(gè)基于react+webpack的多頁(yè)面應(yīng)用配置
這篇文章主要介紹了詳解一個(gè)基于react+webpack的多頁(yè)面應(yīng)用配置,小編覺(jué)得挺不錯(cuò)的,現(xiàn)在分享給大家,也給大家做個(gè)參考。一起跟隨小編過(guò)來(lái)看看吧2019-01-01React路由的history對(duì)象的插件history的使用解讀
這篇文章主要介紹了React路由的history對(duì)象的插件history的使用,具有很好的參考價(jià)值,希望對(duì)大家有所幫助,如有錯(cuò)誤或未考慮完全的地方,望不吝賜教2023-10-10