script标签用于加载和执行脚本,直接在html中使用该标签,浏览器将按照顺序加载和执行脚本从而阻塞DOM的渲染,尤其是使用第三方脚本时,如果出现服务器响应迟缓或者网络延迟较高,浏览器页面会出现长时间的白屏状态,通过script标签的async和defer属性,可以有效减少这种问题的出现
关键词:
DOM渲染
、js脚本加载
、js脚本执行
、异步
defer
script标签设置了defer属性,浏览器会在不影响DOM渲染的情况下异步加载脚本文件(后台加载),在DOM渲染完成后、DOMContentLoaded事件触发前执行脚本,如果有多个script标签设置了该属性,各个脚本会按引入的顺序执行
尝试
- 创建一个HTML
- 在浏览器中执行,查看加载和执行情况
可以看到,脚本2(2.01s)后于脚本1(1.00s)加载完成,但是先执行的是脚本2,定义了defer属性的脚本执行完成后在触发DOMContentLoaded事件
# async
script标签设置了async属性,浏览器会异步在后台加载脚本文件,并在允许的情况下执行脚本,此时的DOM可能还没完成渲染,如果有多个该类型的标签,脚本不一定会按照引入的顺序执行,谁先加载完就马上执行谁,DOMContentLoaded事件先后不定
尝试
- 创建一个HTML脚本
- 浏览器加载和执行情况
可以看到,,DOMContentLoaded事件先触发,脚本也没有按照引入顺序执行
再次尝试
- 创建一个渲染时间较长的HTML脚本
- 查看浏览器执行情况
可以看到,这次DOMContentLoaded事件后触发
可以看到,使用async不会等待dom渲染完成再执行,同时执行顺序也不会按照引入的顺序
甘特图比较
普通脚本
defer脚本
async脚本
使用情景
- defer
在脚本依赖DOM的情况下使用defer
- async
脚本不依赖DOM的情况下使用async