日本免费全黄少妇一区二区三区-高清无码一区二区三区四区-欧美中文字幕日韩在线观看-国产福利诱惑在线网站-国产中文字幕一区在线-亚洲欧美精品日韩一区-久久国产精品国产精品国产-国产精久久久久久一区二区三区-欧美亚洲国产精品久久久久

瀏覽器環(huán)境下JavaScript腳本加載與執(zhí)行探析之defer與async特性( 二 )


瀏覽器環(huán)境下JavaScript腳本加載與執(zhí)行探析之defer與async特性


根據(jù)標準中的定義,內(nèi)部腳本不支持defer,而IE9及以下的瀏覽器則提供了內(nèi)部腳本的defer支持 。
2.2 defer的瀏覽器支持情況
下面我們來看一下defer特性的瀏覽器支持情況:
瀏覽器環(huán)境下JavaScript腳本加載與執(zhí)行探析之defer與async特性


IE9及以下的瀏覽器存在一個bug,這個bug將在稍后的DEMO中進行詳細的說明 。
2.3 DEMO:defer特性的功能驗證
我們模仿在Olivier Rochard在《the script defer attribute》使用的方式來驗證一下defer特性的功能:
首先我們準備了6個外部腳本:
1.js:
test= "我是head外部腳本";
2.js
test= "我是body外部腳本";
3.js
test= "我是底部外部腳本";
defer1.js
test= "我是head外部延遲腳本";
defer2.js
test= "我是body外部延遲腳本";
defer3.js
test= "我是底部外部延遲腳本";
HTML中的代碼為:
瀏覽器環(huán)境下JavaScript腳本加載與執(zhí)行探析之defer與async特性


代碼中,為了方便實現(xiàn)DOMContentLoaded事件,我們引入了jQuery(之后的文章還會再介紹如何自己實現(xiàn)兼容的DOMContentLoaded),然后,我們在腳本的head內(nèi)、body內(nèi)部和body外部分別引入延遲腳本和正常腳本,并且通過一個全局的字符串來記錄每一段代碼的執(zhí)行狀態(tài),我們看一下各個瀏覽器中的執(zhí)行結(jié)果:
瀏覽器環(huán)境下JavaScript腳本加載與執(zhí)行探析之defer與async特性


從輸出的結(jié)果中我們可以確定,只有IE9及以下瀏覽器支持內(nèi)部延遲腳本,并且defer后的腳本都會在DOMContentLoaded事件之前觸發(fā),因此也是會堵塞DOMContentLoaded事件的 。
2.4 DEMO:IE<=9的defer特性bug
從2.3節(jié)中的demo可以看出,defer后的腳本還是能夠保持執(zhí)行順序的,也就是按照添加的順序依次執(zhí)行 。而在IE<=9中,這個問題存在一個bug:假如我們向文檔中增加了多個defer的腳本,而且之前的腳本中有appendChild,innerHTML,insertBefore,replaceChild等修改了DOM的接口調(diào)用,那么后面的腳本可能會先于該腳本執(zhí)行 ??梢詤⒖糶ithub的issue:https://github.com/h5bp/lazyweb-requests/issues/42
我們通過DEMO驗證一下,首先修改1.js的代碼為(這段代碼只為模擬,事實上這段代碼存在極大的性能問題):
document.body.innerHTML = "
我是后來加入的
";


document.body.innerHTML= "
我是后來加入的
";


document.body.innerHTML= "
我是后來加入的
";


document.body.innerHTML= "
我是后來加入的
";


document.body.innerHTML= "
我是后來加入的
";


document.body.innerHTML= "
我是后來加入的
";


document.body.innerHTML= "
我是后來加入的
";


alert("我是第1個腳本");
2.js
alert("我是第2個腳本");
修改HMTL中的代碼為:
瀏覽器環(huán)境下JavaScript腳本加載與執(zhí)行探析之defer與async特性


正常情況下,瀏覽器中彈出框的順序肯定是:我是第1個腳本-》我是第2個腳本,然而在IE<=9中,執(zhí)行結(jié)果卻為:我是第2個腳本-》我是第1個腳本,驗證了這個bug 。
2.5 defer總結(jié)
在總結(jié)之前,首先要說一個注意點:正如標準中提到的,defer的腳本中不應(yīng)該出現(xiàn)document.write的操作,瀏覽器會直接忽略這些操作 。
總的來看,defer的作用一定程度上與將腳本放置在頁面底部有一定的相似,但由于IE<=9中的bug,如果頁面中出現(xiàn)多個defer時,腳本的執(zhí)行順序可能會被打亂從而導(dǎo)致代碼依賴可能會出錯,因此實際項目中很少會使用defer特性,而將腳本代碼放置在頁面底部可以替代defer所提供的功能 。

推薦閱讀