Promise 与异步编程
Promise 是异步操作的“承诺”:pending → fulfilled / rejected 三态,状态一旦敲定不可逆。then 返回新 Promise,因此可以链式调用;未处理的 rejection 会在事件循环末尾触发 unhandledrejection 事件。
手写 Promise 是高频题,核心是“发布订阅 + then 返回新 Promise”:resolve / reject 把回调存入数组,状态敲定后依次执行。实际项目中常考四个并发 API:Promise.all(全成才 resolve,一个失败即失败)、Promise.race(第一个落定者胜出,不论成败)、Promise.allSettled(等全部落定,结果带 status)、Promise.any(首个成功者,全失败才失败)。
- 三态不可逆;then 返回新 Promise 实现链式调用
- all 全成才成功,allSettled 等全部落定,race 看最快,any 看首个成功
- Promise 本质是回调函数的发布订阅 + 状态机
JS
// 四个并发 API 对比 const p = (name, ms, ok = true) => new Promise((res, rej) => setTimeout(() => (ok ? res(name) : rej(name)), ms)); Promise.all([p('A', 30), p('B', 20)]).then(r => console.log('all:', r)); // [A, B] Promise.race([p('A', 30), p('B', 20)]).then(r => console.log('race:', r)); // B(最快落定) Promise.allSettled([p('A', 10), p('B', 20, false)]).then(r => console.log('settled:', r)); Promise.any([p('A', 20, false), p('B', 30)]).then(r => console.log('any:', r)); // B // 简化版手写 Promise(核心思路) class MyPromise { constructor(executor) { this.state = 'pending'; this.cbs = []; // 订阅:then 的回调 const settle = (state, val) => { if (this.state !== 'pending') return; // 状态不可逆 this.state = state; this.value = val; this.cbs.forEach(cb => cb()); // 状态敲定,通知订阅者 }; executor(v => settle('fulfilled', v), e => settle('rejected', e)); } then(onOk, onFail) { return new MyPromise((res, rej) => { const handle = () => { // 微任务时机 + 递归 then queueMicrotask(() => { const fn = this.state === 'fulfilled' ? onOk : onFail; try { res(fn(this.value)); } catch (e) { rej(e); } }); }; this.state === 'pending' ? this.cbs.push(handle) : handle(); }); } } new MyPromise(r => setTimeout(() => r('手写成功'), 50)) .then(v => console.log(v));
本节要点Promise = 三态状态机 + 回调订阅;四个并发 API 的差异(all / allSettled / race / any)要一句话说清。




