深入解析 HTML 中 `<script>` 标签的 async 和 defer 属性

发布于:2025-04-14 ⋅ 阅读:(22) ⋅ 点赞:(0)

一、背景与问题

在网页性能优化中,脚本的加载和执行方式直接影响页面渲染速度和用户体验。传统 <script> 标签的阻塞行为可能导致页面“白屏”,而 asyncdefer 属性提供了非阻塞的解决方案。本周重点研究二者的差异、适用场景及实际应用。


二、核心概念解析

1. 默认 <script> 的行为

  • 阻塞 HTML 解析‌:浏览器遇到 <script> 标签时,会暂停 HTML 解析,下载并执行脚本,完成后继续解析。
  • 问题‌:大脚本或网络延迟时,显著延长页面渲染时间。

2. async 属性

  • 行为‌:
    • 脚本异步下载(与 HTML 解析并行)。
    • 下载完成后立即执行‌,执行时会再次阻塞 HTML 解析。
  • 特点‌:
    • 脚本执行顺序‌不确定‌(先下载完的先执行)。
    • 适用于‌独立且无依赖‌的脚本(如统计分析、广告 SDK)。

3. defer 属性

  • 行为‌:
    • 脚本异步下载(与 HTML 解析并行)。
    • 脚本延迟到 ‌HTML 解析完成后、DOMContentLoaded 事件前‌ 按顺序执行。
  • 特点‌:
    • 执行顺序与声明顺序‌严格一致‌。
    • 适用于‌依赖 DOM 或其他脚本‌的场景(如页面初始化逻辑)。

4. 对比表格

属性 加载方式 执行时机 执行顺序 适用场景
默认 同步 立即执行 按声明顺序
async 异步 下载完立即执行 不确定 独立脚本(如 GA 统计)
defer 异步 HTML 解析后顺序执行 按声明顺序 依赖型脚本

三、示例与验证

代码示例

<script src="script1.js" async></script>  
<script src="script2.js" defer></script>  
<script src="script3.js"></script>

执行顺序模拟
默认脚本‌:script3.js 阻塞 HTML 解析,优先执行。
async 脚本‌:若 script1.js 下载速度快于 HTML 解析,可能先于 defer 脚本执行。
defer 脚本‌:script2.js 在 HTML 解析完成后按顺序执行。
四、最佳实践
优先使用 defer‌:确保脚本顺序执行且不阻塞渲染。
谨慎使用 async‌:仅用于无依赖的第三方脚本。
动态脚本‌:通过 document.createElement('script') 插入的脚本默认具有 async 行为。
五、兼容性与注意事项
兼容性‌:
defer 支持所有主流浏览器(包括 IE10+)。
async 不支持 IE9 及以下。
注意点‌:同时使用 async 和 defer 时,现代浏览器以 async 优先。

附录‌

MDN 文档
测试 Demo 链接(可选)
text
Copy Code

### 说明  
1. &zwnj;**兼容性**&zwnj;:此 Markdown 文件可被所有支持 Markdown 的工具(如 Typora、VS Code、GitHub)正确解析。  
2. &zwnj;**语法重点**&zwnj;:  
   - 代码块用 ` ````包裹,并指定语言(如 `html`)。  
   - 表格使用 `|` 分隔列,`---` 分隔表头。  
   - HTML 标签用反引号包裹避免解析冲突(如 ``<script>``)。

网站公告

今日签到

点亮在社区的每一天
去签到