await挂起异步函数执行上下文而非线程,仅限async函数内使用;等待Promise或thenable对象,后续代码作为微任务执行,不阻塞主线程。
await 不会挂起“线程”,它挂起的是当前 异步函数的执行上下文,让出控制权给事件循环,以便其他任务可以运行。JavaScript 是单线程的,没有真正的线程概念(主线程上无多线程抢占),所以“挂起线程”这种说法容易引发误解。
这是语法硬性要求。直接在普通函数或顶层作用域写 await somePromise() 会报语法错误。
async function foo() { await fetch('/api'); }
function bar() { await fetch('/api'); }(SyntaxError)await 后面表达式会被自动 Promise.resolve() 包装。它真正等待的是该 Promise 进入 fulfilled 或 rejected 状态。
await 123 → 等价于 await Promise.resolve(123),立刻继续执行await fetch(url) → 等待网络响应完成并返回 Response 对象await new Promise(r => setTimeout(r, 1000)) → 等待 1 秒后 resolve当 await 后的 Promise 完成时,后续语句不会立刻同步运行,而是作为微任务(microtask)被调度,在当前同步代码结束后、下一次宏任务(如 setTimeout)之前执行。
await a(); console.log('1'); await b(); console.log('2'); 中,'1' 一定在 a() 的 Promise fulfilled 后打印,'2' 同理比如 await setTimeout(...) 是无效的——setTimeout 返回的是定时器 ID(数字),不是 Promise,await 会立刻解包并继续,达不到延时效果。
await new Promise(r => setTimeout(r, 1000));
await setTimeout(() => {}, 1000);(毫无等待作用)理解 await 的本质是“暂停函数执行、交还控制权、等待 Promise settled 后恢复”,比记住“挂起线程”更准确也更实用。