跳到主要内容

前言

日常开发中,我们使用的 script 标签基本上恒定在三种

  • 带 defer 的
  • 带 async 的
  • 什么都没带的

如下

20230301134328

这三种主要是决定浏览器对于 js 解析和执行是否阻塞 html 解析

我们看看详细分析。

< script src="" > (不带 async 和 defer 的)

图片注释:

 绿色(html解析过程)
灰色(html暂停解析过程)
紫色(script下载过程)
红色(script执行过程)

不带 async 和 defer 的 script 标签会阻塞 html 的解析

20230301134408

(原图地址:async vs defer attributes - Growing with the Web

由图得知:在 script 标签同时不具备 defer 和 async 的情况下。script 标签的下载和执行都会阻塞 html 的渲染。

< script src="" async> (带 async 不带 defer 的)

只有 async 的 script 标签可能会阻塞 html 的解析

20230301134448

(原图地址:async vs defer attributes - Growing with the Web

由图得知:在 script 标签在有 async 的情况下。script 标签的下载是异步的,不会阻塞 html 的渲染,但是 script 的执行依然会阻塞 html 的解析。

但这里有一个问题:为什么上面说:只有 async 的 script 标签可能会阻塞 html 的解析,为什么是可能会而不是一定会?有没有可能不会阻塞。

有。

20230301134527

(图片地址:自己 P 的,没有来源地址)

比如如上情况,我们加载 script 完毕的时候,html 已经解析完成了。那么这个时候再去执行 script 就不会阻塞 html 解析。

< script src="" defer> (带 defer 不带 async 的)

只有 defer 的 script 标签不会阻塞 html 的解析

20230301134542

(原图地址:async vs defer attributes - Growing with the Web

如图:仅仅携带 defer 属性的 script 标签加载是异步的,所以加载不会阻塞 html 解析。加载完成之后也不会马上执行,而是等待 html 解析完毕之后再执行,所以执行也不会阻塞 html 的渲染。

还有几个小问题

如果 script 标签同时具备 async 和 defer 会有什么效果?

在 script 同时具备 async 和 defer 的情况下。不论先后顺序,效果和 async 是一样的。

如果有多个携带 defer 属性的 script 标签,他们的执行顺序会乱吗?

不会。如果有多个携带 defer 属性的 script 标签。他们的执行顺序是根据我们编码的顺序去执行的,所以不用担心他们之间的依赖关系。

但是以上都是针对 script 放在 head 的时候出现的情况。写过 jq 的小伙伴都应该会一种操作,就是把 script 标签放到 body 之后去写,这样,即便不写 async 和 defer 也可防止 script 标签阻塞 html 解析。

信息

作者:工边页字 链接:https://juejin.cn/post/7187315516472557626 来源:稀土掘金 著作权归作者所有。商业转载请联系作者获得授权,非商业转载请注明出处。