常见手写题

25 阅读5分钟

⚡ 第一章 必刷:异步编程与并发控制 (Top Priority)

大厂考察率 90%。如果这部分写不出来,面试大概率会挂。

  • 1.1 带并发限制的异步调度器 (Scheduler) ⭐⭐⭐⭐⭐ (字节/阿里高频)
    • 题目:实现 Scheduler 类,add(promiseCreator),同时运行任务最多 N 个。
    • 变种:要求实现一个 asyncPool(limit, tasks) 函数。
    • 关键点:等待队列、递归调用 next()、Promise 链式衔接。
  • 1.2 完整版 Promise A+ 实现 ⭐⭐⭐⭐⭐
    • 题目:手写 Promise,通过 Promises-aplus-tests 测试。
    • 关键点:状态机 (Pending/Fulfilled/Rejected)、then 的微任务机制 (queueMicrotask/MutationObserver)、链式调用返回新 Promise、值穿透。
  • 1.3 Promise 静态方法全家桶 ⭐⭐⭐⭐
    • Promise.all:Fail-fast 机制(一个挂全挂)。
    • Promise.allSettled:记录所有结果。
    • Promise.race:竞态机制。
    • Promise.any:只求一个成功。
  • 1.4 异步流控制:LazyMan ⭐⭐⭐⭐ (微信/美团高频)
    • 题目LazyMan('Joe').eat('lunch').sleep(3).eat('dinner').sleepFirst(2)
    • 关键点:任务队列 (Task Queue)、中间件思想、next 触发、优先队列处理 sleepFirst
  • 1.5 消除异步传染性 (Async/Await 原理) ⭐⭐⭐
    • 题目:手写 Generator 的自动执行器 (类似 co 库)。
    • 关键点:递归调用 next,判断 done 状态,处理 yield 后面的 Promise。
  • 1.6 精准倒计时 / 修正版 setInterval ⭐⭐⭐
    • 题目:用 setTimeout 模拟 setInterval,并解决时间偏移 (Drift) 问题。
    • 关键点:计算 Date.now() 的偏差值,动态调整下一次 setTimeout 的 delay。
  • 1.7 交通灯问题 ⭐⭐⭐
    • 题目:红灯 3s,绿灯 1s,黄灯 2s,循环打印。
    • 关键点await 配合 sleep 函数,死循环 while(true)

🧬 第二章 核心:JS 语言底层与模拟

考察基础扎实程度,切记不要忽略 Edge Cases。

  • 2.1 完美的深拷贝 (Deep Clone) ⭐⭐⭐⭐⭐
    • 题目:实现 deepClone(obj)
    • 关键点
      1. 循环引用:必须用 WeakMap 记录已拷贝对象。
      2. 特殊类型DateRegExpSetMapSymbol 需要特殊处理。
      3. 原型链:是否保留原型链?(一般考察保留)。
  • 2.2 继承的终极方案 ⭐⭐⭐⭐
    • 题目:寄生组合式继承 (Parasitic Combination Inheritance)。
    • 关键点Object.create 断开父子引用共享,修复 constructor 指向。
  • 2.3 new 操作符模拟 ⭐⭐⭐
    • 关键点:创建一个对象 -> 原型链接 -> 绑定 this 执行构造函数 -> 判断返回值类型。
  • 2.4 call / apply / bind 模拟 ⭐⭐⭐⭐
    • 关键点:将函数设为对象的属性 (context.fn = this) 执行,使用 Symbol 避免属性冲突,bind 支持柯里化和 new 调用。
  • 2.5 instanceof 原理 ⭐⭐⭐
    • 关键点right.prototype 是否在 left 的原型链 (__proto__) 上。
  • 2.6 对象相关 API
    • Object.create(proto) Polyfill。
    • Object.is(a, b):处理 NaN 等于 NaN+0 不等于 -0
    • Object.freeze:递归冻结对象。

🛠️ 第三章 工具:Lodash/Ramda 风格函数库

考察代码抽象能力和逻辑复用。

  • 3.1 函数柯里化 (Currying) ⭐⭐⭐⭐
    • 题目add(1)(2, 3)(4)
    • 进阶:支持占位符 _ 的柯里化 (难点)。
  • 3.2 组合函数 (Compose / Pipe) ⭐⭐⭐
    • 题目compose(f, g, h)(x) 等价于 f(g(h(x)))
    • 关键点funcs.reduce((a, b) => (...args) => a(b(...args)))
  • 3.3 防抖 (Debounce) & 节流 (Throttle) ⭐⭐⭐⭐⭐
    • 要求:手写高级版,支持 leading (前沿触发)、trailing (后沿触发) 和 cancel (取消)。
  • 3.4 数组与对象处理
    • 数组扁平化flat (指定层级),递归或 reduce
    • 数组去重unique (处理对象去重,根据内容判断)。
    • 对象扁平化flattenObj({a:{b:1}}) -> {'a.b': 1}
    • 深合并 (Deep Merge):递归合并两个对象配置。
    • Get / Setget(obj, 'a[0].b') 安全访问与赋值。
  • 3.5 Memoize (函数缓存) ⭐⭐⭐
    • 题目:缓存函数计算结果。
    • 关键点:自定义 resolver 生成 Cache Key (如 JSON.stringify(args)).
  • 3.6 数组乱序 (Shuffle) ⭐⭐⭐
    • 算法:Fisher-Yates 洗牌算法 (从后往前遍历,随机交换)。

⚛️ 第四章 框架:Vue/React 源码级复现

P6+ 必须具备造简易轮子的能力。

  • 4.1 发布订阅模式 (EventEmitter) ⭐⭐⭐⭐⭐
    • APIon, emit, off, once
    • 注意off 时如何处理 once 包裹的函数。
  • 4.2 观察者模式 (Observer) ⭐⭐⭐
    • 场景:Vue 的 Dep 和 Watcher 关系。
  • 4.3 Vue2/3 响应式原理对比实现 ⭐⭐⭐⭐⭐
    • Vue2defineReactive (Object.defineProperty),数组方法的劫持 (重写 push/pop 等)。
    • Vue3reactive (Proxy),Reflect 配合使用,处理嵌套对象。
  • 4.4 简易 Redux ⭐⭐⭐⭐
    • 核心createStore (闭包保存 state),dispatch 触发 listeners
    • 中间件原理applyMiddleware (洋葱模型,compose)。
  • 4.5 React Hooks 原理模拟 ⭐⭐⭐⭐
    • 题目:用闭包/数组模拟 useStateuseEffect
    • 关键点:依赖项比对 (depsChanged),Hook 链表/索引顺序的重要性。
  • 4.6 虚拟 DOM 转真实 DOM ⭐⭐⭐
    • 题目render(h('div', {}, ['text']))
    • 关键点:递归创建节点,设置属性。

🌲 第五章 算法:前端高频数据结构与算法

不考红黑树,只考前端应用场景强相关的算法。

5.1 树与列表转换 (必考)

  • 列表转树 (List to Tree) ⭐⭐⭐⭐⭐:O(n) 复杂度,使用 Map 建立引用映射。
  • 树转列表 (Tree to List) ⭐⭐⭐⭐:DFS (递归) 或 BFS (迭代)。
  • 查找树节点路径:给定 ID 查找完整路径数组。

5.2 常见算法

  • LRU 缓存 (Least Recently Used) ⭐⭐⭐⭐⭐:Map (利用迭代顺序) 或 双向链表+Hash。
  • 大数相加 / 相乘 ⭐⭐⭐⭐:字符串逐位模拟。
  • 版本号排序 ⭐⭐⭐:分割字符串,逐位比较。
  • 有效的括号 ⭐⭐⭐:栈 (Stack) 的应用。
  • 最长无重复子串 ⭐⭐⭐⭐:滑动窗口 (Sliding Window)。
  • 两数之和 / 三数之和 ⭐⭐⭐:Map 缓存 / 双指针。
  • 全排列 ⭐⭐⭐:回溯算法 (Backtracking)。
  • Top K 问题 ⭐⭐⭐⭐:数组中第 K 大的元素 (快排变种 QuickSelect 或 最小堆)。

5.3 字符串与解析

  • 解析 URL 参数 (Query String):正则或 split,注意解码。
  • 模板引擎实现render('{{ name }}', data),正则替换。
  • 千分位格式化1234567 -> 1,234,567 (正则或循环取余)。

🌐 第六章 场景:浏览器、网络与工程化设计

考察解决实际问题的能力。

  • 6.1 图片懒加载 (Lazy Load) ⭐⭐⭐⭐
    • 方案IntersectionObserver API (现代) 或 getBoundingClientRect + 节流 (传统)。
  • 6.2 JSONP 实现 ⭐⭐⭐
    • 关键点:动态创建 script,全局 callback,清理收尾。
  • 6.3 AJAX (XHR) 封装 ⭐⭐⭐
    • 关键点XMLHttpRequest 状态监听,Promise 封装。
  • 6.4 前端路由原理 (Router) ⭐⭐⭐⭐
    • Hash 模式hashchange 事件。
    • History 模式pushState, replaceState, popstate 事件。
  • 6.5 虚拟列表 (Virtual List) ⭐⭐⭐⭐⭐
    • 题目:定高虚拟列表的核心计算。
    • 关键点startIndex, endIndex, paddingTop, paddingBottom 的计算公式。
  • 6.6 请求重试与并发池 (结合) ⭐⭐⭐⭐⭐
    • 场景:文件分片上传,控制并发数,且每个分片失败后可重试 2 次。

💡 P6+ 面试评分表 (Self-Check)

维度P5 (初中级)P6 (高级/资深)P7 (专家)
功能实现能跑通,有 BugBug Free,考虑边界完美运行,逻辑优雅
代码风格随意,命名不规范规范,ES6+,语义化易读,模块化,高内聚
类型系统无或 AnyScript熟练使用 TypeScript 泛型复杂的类型推导
性能意识暴力解法空间/时间复杂度优化极致优化,考虑 GC
扩展性硬编码参数配置化设计模式解耦

祝你面试顺利,Offer 拿到手软! 🚀