第十八节:代码手写题-实现一个简版useState

简版 useState 实现原理与代码解析

一、核心设计思路

useState 的核心原理是通过 闭包状态数组 实现状态存储与更新。以下是关键实现要素:

  1. 状态存储:使用外部变量 states 数组保存所有状态值,setters 数组保存对应的更新函数。
  2. 顺序管理:通过 cursor 游标记录当前操作的索引,确保多次 useState 调用的状态按顺序存取。
  3. 更新触发:调用 setState 时会修改对应状态值,并触发组件重新渲染(模拟 ReactDOM.render)。
二、完整实现代码
// 外部存储状态与更新函数
let states = [];
let setters = [];
let cursor = 0;
let isInitialRender = true;

function createSetter(cursor) {
  return function (newState) {
    // 支持函数式更新(如 setCount(prev => prev + 1))
    if (typeof newState === 'function') {
      states[cursor] = newState(states[cursor]);
    } else {
      states[cursor] = newState;
    }
    // 触发重新渲染(模拟 React 的渲染流程)
    render();
  };
}

function useState(initialState) {
  // 首次渲染初始化状态
  if (isInitialRender) {
    states.push(initialState);
    setters.push(createSetter(cursor));
    isInitialRender = false;
  }

  // 获取当前状态和对应更新函数
  const currentState = states[cursor];
  const setState = setters[cursor];

  // 移动游标为下一次 useState 调用做准备
  cursor++;

  return [currentState, setState];
}

// 模拟组件重新渲染(实际 React 中通过调度器触发)
function render() {
  cursor = 0; // 重置游标
  ReactComponent(); // 重新执行组件函数
}

// 使用示例
function Counter() {
  const [count, setCount] = useState(0);
  const [name, setName] = useState("Anonymous");

  return (
    <div>
      <p>Count: {count}</p>
      <button onClick={() => setCount(c => c + 1)}>+1</button>
      <p>Name: <input value={name} onChange={e => setName(e.target.value)}/></p>
    </div>
  );
}
三、关键特性实现
特性实现方式引用来源
多状态管理通过 cursor 游标按调用顺序存取 statessetters 数组
函数式更新setState 参数支持函数类型,基于前值计算新值
状态持久化使用闭包保存 states 数组,避免组件重新执行时状态丢失
渲染触发机制调用 setState 后执行 render() 重置游标并重新执行组件函数
四、与 React 源码的差异
特性简版实现React 实际实现
状态存储结构数组链表(Fiber 节点的 memoizedState
更新批量处理无(立即触发渲染)异步批处理(避免多次渲染)
依赖追踪通过 Effect List 追踪副作用
错误处理无边界条件检查严格模式校验调用顺序
五、使用注意事项
  1. 顶层调用限制:必须在组件顶层调用,不能在条件语句/循环中使用(依赖 cursor 顺序)
  2. 性能缺陷:每次更新都会全量重新渲染组件,无 Diff 优化
  3. 闭包陷阱:异步操作中使用闭包可能捕获旧状态(需通过函数式更新解决)
六、扩展思考

若需要实现更接近 React 的版本,可参考以下优化方向:

  1. 链表结构:用 { memoizedState, next } 链表替代数组(见网页2的进阶版实现)
  2. 批量更新:通过队列收集多次 setState 调用,合并为单次渲染
  3. 优先级调度:模拟 React 的并发模式更新优先级

通过这个简化实现,可以深入理解 React Hooks 的闭包管理、状态更新触发机制等核心原理。实际开发中应始终使用 React 官方提供的 Hooks API 以获得最佳性能和稳定性。

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值