本文将讲解useState
钩子的实现。useState
是基于useReducer
实现的。其reducer函数为:
function basicStateReducer<S>(state: S, action: BasicStateAction<S>): S {
// $FlowFixMe: Flow doesn't like mixed types
return typeof action === 'function' ? action(state) : action;
}
Mount阶段
useState
的这个阶段和useReducer
所完成的事情是一样,只是其reducer为basicStateReducer
,而useReducer
是由参数传入:
-
useState
首先调用mountWorkInProgressHook
创建一个Hook对象 - 然后,计算初始状态值
initialState
,该值可以是由第二个参数(当不传第三个参数时)传入,也可由第三个参数(只能是函数)和第二个参数计算所得。 - 创建
queue
以及dispatch
函数 - 返回初始值
initialState
以及dispatch
函数
function mountState<S>(
initialState: (() => S) | S,
): [S, Dispatch<BasicStateAction<S>>] {
const hook = mountWorkInProgressHook();
if (typeof initialState === 'function') {
// $FlowFixMe: Flow doesn't like mixed types
initialState = initialState();
}
hook.memoizedState = hook.baseState = initialState;
const queue = (hook.queue = {
pending: null,
dispatch: null,
lastRenderedReducer: basicStateReducer,
lastRenderedState: (initialState: any),
});
const dispatch: Dispatch<
BasicStateAction<S>,
> = (queue.dispatch = (dispatchAction.bind(
null,
currentlyRenderingFiber,
queue,
): any));
return [hook.memoizedState, dispatch];
}
Update阶段
这个阶段是直接调用的updateReducer
,其逻辑大体与updateReducer
相同。
function updateState<S>(
initialState: (() => S) | S,
): [S, Dispatch<BasicStateAction<S>>] {
return updateReducer(basicStateReducer, (initialState: any));
}
网友评论