React Hooks源码深度解析

2023-05-28 0 1,088

译者:天猫零售业郑炳懿

序言

React Hooks是React16.8导入的三个新优点,它容许表达式模块中采用state和其它 React 优点,而无须采用类模块。Hooks是三个十分关键的基本概念,即使它提供了更单纯、更更易认知的React合作开发新体验。

React Hooks的核心理念源代码主要就主要就包括三个部份:React外部的Hook命令行和一连串实用工具的Hook表达式。

具体来说,让他们看呵呵React外部的Hook命令行。那个命令行是React外部的三个关键监督机制,它全权负责管理模块中的大部份Hook,并保证它在模块图形前夕以恰当的顺序调用。

外部Hook命令行

实例:

const Hook ={ queue:[], current: null,};function useState(initialState){ const state = Hook.current[Hook.queue.length]; if (!state){ Hook.queue.push({ state: typeof initialState ===function? initialState(): initialState, setState(value){ this.state = value; render();},});} return [state.state, state.setState.bind(state)];}function useHook(callback){ Hook.current ={ proto: Hook.current,}; try { callback();} finally { Hook.current = Hook.current.proto;}}function render(){ useHook(()=>{ const [count, setCount]= useState(0); console.log(count:, count); setTimeout(()=>{ setCount(count +1);},1000);});}render();

在那个实例中,Hook第一类有三个重要特性:queue和current。queue储存模块中大部份Hook的状况和预览表达式,current储存现阶段已经开始图形的模块的Hook二叉树。useState和useHook表达式则依次负责管理建立捷伊Hook状况和在模块中采用Hook。

实用工具 Hook 表达式

useState Hook

以下是useState Hook的实现实例:

function useState(initialState){ const hook = updateWorkInProgressHook(); if (!hook.memoizedState){ hook.memoizedState =[ typeof initialState ===function? initialState(): initialState, action =>{ hook.queue.pending = true; hook.queue.dispatch = action; scheduleWork();},];} return hook.memoizedState;}

上述代码实现了useState Hook,其主要就作用是返回三个state和预览函数的数组,state 初始值为initialState。

ok。它的实现如下:

function updateWorkInProgressHook(){ const fiber = getWorkInProgressFiber(); let hook = fiber.memoizedState; if (hook){ fiber.memoizedState = hook.next; hook.next = null;} else { hook ={ memoizedState: null, queue:{ pending: null, dispatch: null, last: null,}, next: null,};} workInProgressHook = hook; return hook;}

前已经开始执行的hook第一类。在表达式模块中,每三个useState调用都会建立三个捷伊 hook 第一类,并将其添加到fiber第一类的hooks二叉树中。那个hooks二叉树是通过fiber第一类的memoizedState特性来维护的。

他们还需要注意到在useState Hook的实现中,每三个hook第一类都包含了三个queue第一类,用来储存待更捷伊状况以及预览表达式。scheduleWork()表达式则用来通知React调度器有任务需要执行。

在React的源代码中,useState表达式实际上是三个叫做useStateImpl的外部表达式。

下面是useStateImpl的源代码:

function useStateImpl(initialState:(()=> S) S):[S, Dispatch

function resolveDispatcher(): Dispatcher { const dispatcher = currentlyRenderingFiber?.dispatcher; if (dispatcher === undefined){ throw new Error(Hooks can only be called inside the body of a function component.(https://fb.me/react-invalid-hook-call));} return dispatcher;}

明现阶段不在模块的图形过程中,就会抛出三个错误。

最后,他们来看呵呵useState方法在具体的dispatcher实现中是如何实现的。他们以useReducer的

dispatcher为例,它的实现如下:

export function useReducer( reducer:(prevState: S, action: A)=> S, initialState: S, initialAction?: A,):[S, Dispatch]{ const [dispatch, currentState]= updateReducer( reducer,//$FlowFixMe: Flow doesnt like mixed types [initialState, initialAction],//$FlowFixMe: Flow doesnt like mixed types reducer === basicStateReducer ? basicStateReducer : updateStateReducer,); return [currentState, dispatch];}

可以看到,useReducer方法实际上是调用了三个叫做updateReducer的表达式,返回了三个包含现阶段状况和dispatch表达式的数组。updateReducer的实现比较复杂,涉及到了很多细节,这里不再展开介绍。

useEffect Hook

useEffect是React中常用的三个Hook表达式,用于在模块中执行副作用操作,例如访问远程数据、添加/移除事件监听器、手动操作DOM等等。useEffect的核心理念功能是在模块的图形过程结束之后异步执行回调表达式,它的实现方式涉及到 React 中的异步图形监督机制。

以下是useEffect Hook的实现实例:

fuch = useContext(BatchContext);//根据现阶段的图形批次判断是否需要执行回调表达式 if (shouldFireEffect(batch, dependencies)){ callback();} //在模块被卸载时清除现阶段 effect 的状况信息 return ()=> clearEffect(batch);}

在那个实例中,useEffect接收三个参数:回调表达式和依赖项数组。当依赖项数组中的任何三个值发生变化时,

React会在下一次图形时重新执行useEffect中传入的回调表达式。

useEffect表达式的实现方式主要就依赖于React中的异步图形监督机制。当三个模块需要重新图形时,React会将大部份的state预览操作加入到三个队列中,在现阶段图形批次结束之后再异步执行这些预览操作,从而避免在同三个图形批次中连续执行多次预览操作。

在useEffect表达式中,他们通过调方法来清除现阶段effect的状况信息,避免对后续的图形批次产生影响。

总结

总的来说,React Hooks的实现原理并不复杂,它主要就依赖于React外部的fiber数据结构和调度系统,通过这些监督机制来实现对模块状况的管理和预览。Hooks能够让他们在表达式模块中采用状况和其它React优点,使得表达式模块的功能可以和类模块媲美。

除了useState、useEffect等hook,React还有useContext等常用的Hook。它的实现原理也基本相似,都是利用fiber架构来实现状况管理和生命周期钩子等功能。

以上是hook单纯实现实例,它并不是React中实际采用的代码,但是可以帮助他们更好地理解hook的核心理念实现方式。

相关文章

发表评论
暂无评论
官方客服团队

为您解决烦忧 - 24小时在线 专业服务