async/await和defer详解

async/await和defer详解

骚话王又来分享知识了!今天咱们聊聊前端开发中让人又爱又恨的异步编程,主角就是Promise和它的进阶形态------async/await,还有经常被新手搞混的HTML中的async和defer。要是你觉得有用,记得收藏点赞,骚话鬼才持续输出干货!

Promise:异步编程的"诺言"

在JavaScript的世界里,异步操作无处不在,比如网络请求、定时器、文件读取......早年间大家用回调(callback)解决异步,结果一不小心就掉进了"回调地狱",代码像层层嵌套的俄罗斯套娃,调试起来让人头秃。

Promise横空出世,像是给异步编程打了一针强心剂。它的本质是一个"承诺":我现在还没拿到结果,但我保证将来某一刻会给你答复(要么成功,要么失败)。

Promise的基本用法

举个栗子:

js 复制代码
const promise = new Promise((resolve, reject) => {
  setTimeout(() => {
    resolve('骚话王的承诺兑现了!');
  }, 1000);
});

promise.then(result => {
  console.log(result); // 输出:骚话王的承诺兑现了!
});

Promise让异步代码变得更清晰,但链式调用多了,依然容易让人晕头转向。

骚话王小贴士: Promise有三种状态:pending(进行中)、fulfilled(已成功)、rejected(已失败)。状态一旦改变就不会再变。

async/await:让异步像同步一样丝滑

骚话王要说,async/await就是Promise的"语法糖",让你写异步代码像写同步一样顺滑。async函数返回的本质还是Promise,但你可以用await暂停代码执行,等Promise有结果再往下走。

async的用法

只要在函数前加上async,这个函数就会自动返回一个Promise。

js 复制代码
async function foo() {
  return '骚话王又来啦!';
}

foo().then(res => console.log(res)); // 输出:骚话王又来啦!

await的魔力

await只能在async函数里用,它会"等待"Promise的结果,代码看起来就像同步一样。

js 复制代码
async function getData() {
  const result = await promise;
  console.log(result); // 输出:骚话王的承诺兑现了!
}

getData();

是不是很丝滑?再也不用写一堆.then(),也不用担心回调嵌套。

错误处理也优雅

用try/catch包裹,异步错误也能像同步一样捕获。

js 复制代码
async function fetchData() {
  try {
    const res = await fetch('https://api.example.com/data');
    const data = await res.json();
    console.log(data);
  } catch (err) {
    console.error('骚话王捕获到错误:', err);
  }
}

骚话王小贴士: await后面可以接任何Promise对象,也可以接普通值,普通值会被自动包装成已resolve的Promise。

async/await和Promise的关系

记住,async/await不是替代Promise,而是让Promise更好用。它们是"亲兄弟",async/await只是让你写代码更优雅。

常见误区提醒: async/await不能脱离Promise单独存在,await只能在async函数里用。

html中的async和defer小科普

顺带一提,deferasync是script标签的两个属性,和js的async/await没啥直接关系,但经常被新手搞混。它们的作用都是优化外部JS脚本的加载和执行时机,避免页面渲染被阻塞。

骚话王这里给大家掰扯掰扯浏览器加载JS时的"阻塞"机制:

  • 普通的<script src="...">:浏览器解析到script标签时,会立刻暂停(阻塞)HTML的解析,去下载并执行JS,等JS执行完了才继续解析后面的HTML。这就像你正写作业,突然被喊去倒垃圾,必须干完才能回来继续。

  • <script src="..." defer>:加了defer后,浏览器遇到script标签不会立刻执行,而是等到HTML文档解析完毕(DOMContentLoaded事件前)再统一顺序执行所有defer脚本。这样页面内容能更快显示,用户体验更好。

  • <script src="..." async>:async和defer有点像,但async脚本下载完就立刻执行(不等HTML解析),执行时同样会阻塞HTML解析,但多个async脚本执行顺序不确定。

举个例子:

html 复制代码
<!-- 阻塞型 -->
<script src="a.js"></script>
<p>骚话王的段落</p>

<!-- defer型 -->
<script src="b.js" defer></script>
<p>骚话王的段落</p>

如果a.js很大,页面会卡在script标签那里,p标签内容迟迟不显示;而b.js用defer,p标签能立刻渲染出来,b.js等HTML都解析完再执行。

骚话王友情提醒:

  • defer和async只对外部脚本有效,内联脚本用不了。
  • defer和async不能同时用,选一个就行。
  • 多个defer脚本会按顺序执行,多个async脚本顺序不确定。
  • 推荐将重要依赖脚本用defer,统计类脚本用async。

Promise是异步的基石,async/await让异步代码优雅如诗。html中的async和defer则是前端性能优化的利器。学会这套组合拳,异步编程和页面性能再也不是拦路虎!

如果觉得骚话鬼才的分享有用,别忘了点赞收藏,关注我,持续解锁更多前端骚操作!

相关推荐
Patrick_Wilson10 小时前
修好 bug 只是开始:一次由监控需求反向重构日志结构的复盘
前端·监控·数据可视化
kyriewen10 小时前
面试官让我优化一个卡死的表格,我打开 Claude 五秒重写,他放下咖啡问我要不要来当组长
前端·javascript·面试
小粉粉hhh11 小时前
React(二)——dom、组件间通信、useEffect
前端·javascript·react.js
Csvn11 小时前
🤖 AI 生成前端代码的 5 个典型翻车现场及修复指南
前端
IT_陈寒12 小时前
SpringBoot自动装配坑了我一天,原来问题出在这
前端·人工智能·后端
索西引擎13 小时前
【React】key 属性:协调算法中的元素标识机制与最佳实践
前端·javascript·react.js
只会cv的前端攻城狮13 小时前
动态组件架构设计:从配置到事件驱动全链路解析
前端·vue.js
飞天狗13 小时前
Next.js 16 App Router 实战:服务端组件与流式渲染
前端·next.js
OpenTiny社区13 小时前
TinyEngine 2.11版本发布:AI 进一步融入画布,Vue 工程可一键转DSL
前端·vue.js·github
小雪_Snow13 小时前
JavaScript 中的三种常用事件
开发语言·前端·javascript