无阻塞加载脚本分析[全]


Posted in Javascript onJanuary 20, 2011

由于浏览器是单线程的,因此脚本在载的时候会阻塞下载其它资源;虽然在现在浏览器已经有所改善,但仍然有待改进。
很显然,脚本必须按顺序执行,但没有必要按顺序下载,解决方法:
1。内嵌JS
通常由于页面大小和缓存能带来更多好处,因此外部文件引入JS更好一些;
在少数情况下,比如首页、少量JS情况下尚可接受。
2。XHR Eval
通过XMLHttpRequest从服务器端获取脚本。
主要缺陷是,通过XHR获取的脚本必须部署在和主页面相同的域中。

Ajax.get("test.js", function (xhr) { 
eval(xhr.responseText); 
});

3。XHR注入
使用XHR获取脚本并创建script标签。
同样,通过XHR获取的脚本必须部署在和主页面相同的域中。
Ajax.get('test.js', function (xhr) { 
injectscript(xhr.responseText); 
}); 
function injectscript(scriptText) { 
var s = document.createElement('script'); 
s.text = scriptText; 
document.getElementsByTagName('head')[0].appendChild(s); 
}

4。Script in Iframe
将需要的脚本放入到一个页面中,然后通过iframe来加载该页面。
缺点是iframe本身的开销比较大,另外浏览器安全机制不允许iframe中的js访问跨域的父页面,反之亦然。
5。Script DOM Element
JS动态创建script DOM元素并设置其src属性。
var scriptElem = document.createElement('script'); 
scriptElem.src = 'http://domain.com/test.js'; 
document.ge('head')[0].appendChild(scriptElem);

6。Script Defer
给script标签添加defer属性。
缺点是只有IE和一些新浏览器支持。
<script defer src='test.js'></script>

7。document.write Script Tag
使用document.write把HTML标签script写入页面。
缺点是只有在IE中是并行加载脚本的。
document.write("<script type='text/javascript' src='test.js'><\/script>");

有一个大家不曾广泛讨论的不同点是对于浏览器忙碌状态的影响,包括浏览器的状态栏、进度条、Tab图标以及鼠标。
当你加载多个彼此间有依赖关系的脚本时,还需要一种能够保证执行顺序的技术。
技术    并行下载    可以跨域    存在Script标签    忙碌指示  顺序保证  大小 (bytes)
XHR Eval IE, FF, Saf, Chr, Op no no Saf, Chr - ~500
XHR Injection IE, FF, Saf, Chr, Op no yes Saf, Chr - ~500
Script in Iframe IE, FF, Saf, Chr, Op no no IE, FF, Saf, Chr - ~50
Script DOM Element IE, FF, Saf, Chr, Op yes yes FF, Saf, Chr FF, Op ~200
Script Defer IE, Saf4, Chr2, FF3.1 yes yes IE, FF, Saf, Chr, Op IE, FF, Saf, Chr, Op ~50
document.write Script Tag IE, Saf4, Chr2, Op yes yes IE, FF, Saf, Chr, Op IE, FF, Saf, Chr, Op ~100
在大多数情况下,Script DOM Element是一个好的选择。这种方式适用于所有的浏览器,而且没有跨域的限制,实现起来也非常的简单和易于理解。唯一的缺点是不能保证各个脚本的执行顺序。如果需要加载多个有依赖关系的脚本,应该将这些脚本拼成一个来保证其按需要的顺序执行,或者使用别的技术。
目前异步加载时保持执行顺序的方法有下面几种,由于篇幅原因,暂不详细描述。
单个脚本
1、Hardcoded Callback
2、Window Onload
3、Timer
4、Script Onload
5、Degrading Script Tags
多个脚本
1、Managed XHR
2、DOM Element and Doc Write
本文参考《高性能网站建设进阶指南》
Javascript 相关文章推荐
js不是基础的基础
Dec 24 Javascript
jquery mobile 移动web(5)
Dec 20 Javascript
AngularJS中比较两个数组是否相同
Aug 24 Javascript
AngularJS中的DOM操作用法分析
Nov 04 Javascript
javascript prototype原型详解(比较基础)
Dec 26 Javascript
Vue数据驱动模拟实现5
Jan 13 Javascript
js模仿微信朋友圈计算时间显示几天/几小时/几分钟/几秒之前
Apr 27 Javascript
Avalonjs双向数据绑定与监听的实例代码
Jun 23 Javascript
vsCode安装使用教程和插件安装方法
Aug 24 Javascript
vue安装遇到的5个报错及解决方法
Jun 12 Javascript
vue中组件通信详解(父子组件, 爷孙组件, 兄弟组件)
Jul 27 Javascript
Ant Design Pro 之 ProTable使用操作
Oct 31 Javascript
善用事件代理,警惕闭包的性能陷阱。
Jan 20 #Javascript
jqeury eval将字符串转换json的方法
Jan 20 #Javascript
通过Jquery遍历Json的两种数据结构的实现代码
Jan 19 #Javascript
JQuery动态给table添加、删除行 改进版
Jan 19 #Javascript
jQuery 1.5最新版本的改进细节分析
Jan 19 #Javascript
基于Jquery与WebMethod投票功能实现代码
Jan 19 #Javascript
jQuery '行 4954 错误: 不支持该属性或方法' 的问题解决方法
Jan 19 #Javascript
You might like
Protoss兵种介绍
2020/03/14 星际争霸
php巧获服务器端信息
2006/12/06 PHP
详解php中 === 的使用
2016/10/24 PHP
ThinkPHP3.2框架自定义配置和加载用法示例
2018/06/14 PHP
PHP操作Redis数据库常用方法示例
2018/08/25 PHP
php中使用array_filter()函数过滤数组实例讲解
2021/03/03 PHP
jquery 取子节点及当前节点属性值
2014/07/25 Javascript
JS截取字符串实例详解
2015/11/24 Javascript
基于JS判断iframe是否加载成功的方法(多种浏览器)
2016/05/13 Javascript
js弹出窗口简单实现代码
2017/03/22 Javascript
bootstrap timepicker在angular中取值并转化为时间戳
2017/06/13 Javascript
JS 仿支付宝input文本输入框放大组件的实例
2017/11/14 Javascript
9种改善AngularJS性能的方法
2017/11/28 Javascript
Vue开发Html5微信公众号的步骤
2019/04/11 Javascript
Element PageHeader页头的使用方法
2020/07/26 Javascript
Kettle中使用JavaScrip调用jar包对文件内容进行MD5加密的操作方法
2020/09/04 Javascript
Python的Django框架中的数据过滤功能
2015/07/17 Python
实例讲解Python编程中@property装饰器的用法
2016/06/20 Python
python时间日期函数与利用pandas进行时间序列处理详解
2018/03/13 Python
Python3之手动创建迭代器的实例代码
2019/05/22 Python
利用pyecharts实现地图可视化的例子
2019/08/12 Python
Python制作词云图代码实例
2019/09/09 Python
Python中filter与lambda的结合使用详解
2019/12/24 Python
详解pycharm连接不上mysql数据库的解决办法
2020/01/10 Python
Pytorch十九种损失函数的使用详解
2020/04/29 Python
CSS3 实现童年的纸飞机
2019/05/05 HTML / CSS
Html5饼图绘制实现统计图的方法
2020/08/05 HTML / CSS
船餐厅和泰晤士河餐饮游轮:Bateaux London
2018/03/19 全球购物
英国领先的电子、技术和办公用品购物网站:Ebuyer
2018/04/04 全球购物
同程旅游英文网站:LY.com
2018/11/13 全球购物
市场营销专业求职信
2014/06/17 职场文书
商务专员岗位职责范本
2014/06/29 职场文书
广告艺术设计专业自荐书
2014/07/08 职场文书
运动会广播稿100字
2014/09/14 职场文书
MySQL中varchar和char类型的区别
2021/11/17 MySQL
python处理json数据文件
2022/04/11 Python