Hook 是 React 16.8 的新增特性,它可以讓我們在不編寫class的情況下使用state以及其他的React特性(比如生命周期)
1.什么情況下使用Hooks
官方并不建議我們把原有的 class 組件,大規(guī)模重構(gòu)成 Hooks,而是有一個(gè)漸進(jìn)過程:
首先,原有的函數(shù)組件如果需要自己的狀態(tài)或者需要訪問生命周期函數(shù),那么用 Hooks 是再好不過了;
另外就是,我們可以先在一些邏輯較簡單的組件上嘗試 Hooks ,在使用起來相對較熟悉,且組內(nèi)人員比較能接受的前提下,再擴(kuò)大 Hooks 的使用范圍。
2.對比與class,函數(shù)式組件有哪些優(yōu)勢
State Hook 使得組件內(nèi)的狀態(tài)的設(shè)置和更新相對獨(dú)立,這樣便于對這些狀態(tài)單獨(dú)測試并復(fù)用。
Hook 將組件中相互關(guān)聯(lián)的部分拆分成更小的函數(shù)(比如設(shè)置訂閱或請求數(shù)據(jù)),而并非強(qiáng)制按照生命周期劃分,這樣使得各個(gè)邏輯相對獨(dú)立和清晰
3.hooks 提供的常用的幾個(gè)函數(shù)
(1) useState
useState來自react,需要從react中導(dǎo)入,它是一個(gè)hook
useState 只在初始化時(shí)執(zhí)行一次,后面不再執(zhí)行
u? 參數(shù):初始化值,如果不設(shè)置為undefined; 返回值:數(shù)組,包含兩個(gè)元素;
? 元素一:當(dāng)前狀態(tài)的值(第一調(diào)用為初始化值); 類比于 state中的值
? 元素二:設(shè)置狀態(tài)值的函數(shù);類比于 setState 更新界面
如下代碼
const [counter,setCount] = useState(0) //數(shù)組的結(jié)構(gòu)
return (
<div>
<h2>當(dāng)前計(jì)數(shù) {counter}</h2>
<button onClick={e => setCount( counter + 1 )}>+1</button>
<button onClick={e => setCount( counter - 1 )}>-1</button>
</div>
);
(2)useEffect
useEffect 相當(dāng)于是 componentDidMount,componentDidUpdate 和 componentWillUnmount 這三個(gè)函數(shù)的組合,可以通過傳參及其他邏輯,分別模擬這三個(gè)生命周期函數(shù);
useEffect 第二個(gè)參數(shù)是一個(gè)數(shù)組,如果數(shù)組為空時(shí),則只執(zhí)行一次(相當(dāng)于componentDidMount)
如果數(shù)組中有值時(shí),則該值更新時(shí),useEffect 中的函數(shù)才會執(zhí)行 (相當(dāng)于componentDidUpdate)
如果沒有第二個(gè)參數(shù),則每次render時(shí),useEffect 中的函數(shù)都會執(zhí)行;
effect 中返回的函數(shù)(其清除函數(shù))(頁面銷毀的時(shí)候調(diào)用), (相當(dāng)于componentWillUnmount)
如下代碼
const [counter,setCounter] = useState(0)
const [age,setAge] = useState(18)
useEffect(()=>{
document.title = counter
console.log('1')
return ()=>{
console.log('2')
}
},[counter])
useEffect(()=>{
console.log('3')
})
useEffect(()=>{
console.log('4')
},[counter,age])
useEffect(()=>{
console.log('5')
},[])
return (
<div>
<h2>當(dāng)前計(jì)數(shù):{counter}</h2>
<button onClick={e=>{setCounter(counter+1)}}>+1</button>
<button onClick={e=>{setAge(age+1)}}>+1</button>
</div>
);
(3) useContex
useContext() 狀態(tài)共享的函數(shù)鉤子
該鉤子的作用是,在組件之間共享狀態(tài)。關(guān)于Context這里不再贅述,其作用就是可以做狀態(tài)的分發(fā),在React16.X以后支持,避免了react逐層通過Props傳遞數(shù)據(jù)。
import React, {useState, useContext} from 'react';
function Test1() {
// hook : useState
// useState 本身是一個(gè)函數(shù),來自react包
// const arr = useState(0)
// const state = arr[0]
// const setState = arr[1]
const [counter, setCount] = useState(0)
const AppContext = React.createContext({})
const A = () => {
const {name} = useContext(AppContext)
return (
<p>我是A組件的名字{name}</p>
)
}
const B = () => {
const {name} = useContext(AppContext)
return (
<p>我是B組件的名字{name}</p>
)
}
return (
<AppContext.Provider value={{name: 'hook測試'}}>
<h2>當(dāng)前計(jì)數(shù) {counter}</h2>
<button onClick={e => setCount(counter + 1)}>+1</button>
<button onClick={e => setCount(counter - 1)}>-1</button>
<A></A>
<B></B>
</AppContext.Provider>
);
}
export default Test1;

image.png