[toc]
useCallback 是一个允许你在多次渲染中缓存函数的 React Hook
useContext 是一个 React Hook,可以让你读取和订阅组件中的 context(上下文)
useDeferredValue 是一个 React Hook,可以让你延迟更新 UI 的某些部分
useEffect 是一个 React Hook,它允许你 将组件与外部系统同步
useImperativeHandle 是 React 中的一个 Hook,它能让你自定义由 ref 暴露出来的句柄
useImperativeHandle(ref, createHandle, dependencies?)
useMemo 是一个 React Hook,它在每次重新渲染的时候能够缓存计算的结果
useReducer 是一个 React Hook,它允许你向组件里面添加一个 reducer。
useRef 是一个 React Hook,它能帮助引用一个不需要渲染的值
useState 是一个 React Hook,它允许你向组件添加一个 状态变量
useTransition 是一个帮助你在不阻塞 UI 的情况下更新状态的 React Hook
React Hooks(如 useState、useEffect)的核心原理,本质是React 利用函数组件的 Fiber 节点,通过链表结构存储 Hook 状态,严格按调用顺序匹配,实现状态的持久化与复用。
我会用极简原理 + 核心机制 + 伪代码实现帮你彻底吃透,不绕弯子。
if/for/函数嵌套 里,因为 React 靠调用顺序匹配状态。React 为每个函数组件创建一个 Fiber 节点,节点上有个专门属性:memoizedState。
这个属性是一个单向链表,每个节点对应一个 Hook:
// 伪代码:组件的 Fiber 节点结构
fiberNode = {
memoizedState: {
hook: {
state: 0, // 第一个 Hook:useState(0) 的值
next: {
hook: {
state: false, // 第二个 Hook:useState(false) 的值
next: null, // 链表结尾
},
},
},
},
};
这是 Hooks 最重要的规则:不能在条件/循环中使用 Hooks。 因为 React 不看 Hook 名称,只看调用顺序:
// 正确:顺序固定
function App() {
const [num, setNum] = useState(0); // 顺序 1
const [flag, setFlag] = useState(false); // 顺序 2
}
// 错误:顺序会变,React 匹配失败
function App() {
if (flag) {
const [num, setNum] = useState(0); // 有时执行,有时不执行
}
const [flag, setFlag] = useState(false);
}
setState 时,React 找到对应链表节点,直接修改 state 值;这是 React 官方 useState 的核心简化版,10 行代码看懂本质:
// 全局变量:记录当前组件、当前 Hook 位置
let currentComponentFiber;
let hookIndex;
function useState(initialState) {
// 1. 拿到当前组件的 Hook 链表
const hooks = currentComponentFiber.memoizedState;
// 2. 按 调用顺序 取对应 Hook
const currentHook = hooks[hookIndex];
// 3. 首次渲染:初始化 Hook,存入状态
if (!currentHook) {
hooks[hookIndex] = {
state: initialState, // 存初始值
};
}
// 4. 定义更新函数:修改状态 + 触发重渲染
const setState = (newState) => {
hooks[hookIndex].state = newState; // 更新链表中的状态
renderComponent(); // 触发组件重新渲染
};
// 5. 索引+1,匹配下一个 Hook,返回当前状态
hookIndex++;
return [hooks[hookIndex - 1].state, setState];
}
// 组件渲染时:重置索引,按顺序执行 Hooks
function renderComponent() {
hookIndex = 0; // 关键!每次渲染都从 0 开始
componentFunction(); // 执行函数组件,调用所有 Hooks
}
所有 Hooks 底层逻辑完全一致,只是功能不同:
useEffect:存储「依赖数组 + 回调函数」,对比依赖是否变化,决定是否执行;useRef:存储一个 { current: xxx } 对象,永久不变;useMemo:存储「计算结果 + 依赖」,依赖不变则直接返回缓存结果;useCallback:缓存函数,本质和 useMemo 一样。React Hooks 就是:用 Fiber 节点的链表存储状态,靠固定调用顺序匹配 Hook,重渲染时按顺序读取状态,实现函数组件的状态持久化与副作用管理。