jquery性能优化技巧(一)

本文参考自:  http://www.blueidea.com/tech/web/2009/6737.asp(本文作了大量的修改)

http://www.artzstudio.com/2009/04/jquery-performance-rules/(英文)

参考:http://blog.benhuoer.com/posts/10-tips-for-jquery-performance.html

中级 jQuery 性能指标和调优: http://www.ibm.com/developerworks/cn/web/wa-aj-advjquery/?S_TACT=105AGX52&S_CMP=tec-yesky#resources强烈推荐大家阅读这篇文章

jquery虽在诸多的js类库中性能表现还算优秀, 但毕竟不是在用原生的javascript开发, 性能问题还是需要引起重视的.下面是一些提高jquery性能的技巧,希望对大家有帮助:(文中测试用到的JQuery版本为1.3.2)

  1. 使用jquery最新版本
  2. 合并和最小化脚本
  3. 尽可能多地通过 ID 进行搜索,而不是 CLASS
  4. 给选择器指定前后文
  5. 将jquery对象缓存起来
  6. 使用子查询
  7. 对直接的DOM操作进行限制
  8. 冒泡
  9. 消除无效查询
  10. 推迟到 $(window).load

1. 使用jquery最新版本

   jQuery一直处于不断的开发和改进过程中。 Jonh 和他的团队不断研究着提升程序性能的新方法。

2.合并和最小化脚本文件

     大部分浏览器都不能同时处理多个脚本文件,所以它们都是排队加载——加载时间也相应地延长了。考虑到你网站的每个页面都会加载这些脚本,你应该考虑把它们放到单个文件中,然后利用压缩工具(比如 Dean Edwards )把它们最小化。更小的文件无疑将带来更快的加载速度。JavaScript和CSS压缩的目的是在保持脚本的执行性能的同时,减少数据传递的字节数(可以通过减小原始文件,也可以利用gzip。大多数产品级的网络服务器都把gzip作为HTTP协议的一部分)。— 引自 YUI compressor ,一款 jQuery官方推荐 的压缩脚本的工具。

 

3. 尽可能多地通过 ID 进行搜索,而不是 CLASS

在 jQuery 代码中两种常见的搜索技术是通过元素的 ID 进行搜索和通过元素的 CLASS 进行搜索。在使用常规 JavaScript 的 JavaScript 库之前,通过 ID 查找页面元素还是相当简单的。可以使用 getElementById() 方法快速找到元素。但是如果没有 JavaScript 库,要查找 CLASS 会更加困难,在必要情况下,我们还通过在其 ID 中进行编码帮助查找。使用 jQuery 时,搜索 CLASS 就像搜索页面上的 ID 一样简单,因此这两个搜索似乎是可互换的。然而实际情况并非如此。通过 ID 搜索比通过 CLASS 搜索要快得多。当通过 ID 进行搜索时,jQuery 实际上仅使用内置的getElementById() 方法,但通过 CLASS 进行搜索时必须遍历页面上的所有元素,以查找匹配项。很明显,当页面越大并且越复杂时,通过 CLASS 进行搜索会导致响应非常慢,而通过 ID 进行搜索不会随着页面变大而变慢。在jquery中最快的选择器是ID选择器. 因为它直接来自于Javascript的getElementById()方法.

例如有一段HTML代码:

<div id="content">
<form method="post" action="#">
<h2>交通信号灯</h2>
<ul id="traffic_light">
<li><input type="radio" class="on" name="light" value="red" /> 红色</li>
<li><input type="radio" class="off" name="light" value="yellow" /> 黄色</li>
<li><input type="radio" class="off" name="light" value="green" /> 绿色</li>
</ul>
<input class="button" id="traffic_button" type="submit" value="Go" />
</form>
</div>

  如果采用下面的选择器,那么它是低效的。

var traffic_button = $(".button");

 因为button已经有ID了,我们可以直接使用ID选择器。如下所示:

var traffic_button = $("#traffic_button");

  我对上面两种方法进行了简单的测试,测试代码如下:

<script type="text/javascript">
	$(function() {
	var startTime =  new Date().getMilliseconds();
	for(var i = 0; i < 10000; i++ ){
		var traffic_button = $(".button");
               // var traffic_button = $("#traffic_button");
		}
		var endTime = new Date().getMilliseconds();
		alert(endTime - startTime);
	});
	</script>

 对第一种选择器多次测试结果如下:firefox3.5.8:  650ms   IE8:2200ms

 对第二种选择器多次测试结果如下: firefox3.5.8:  200ms     IE8:1500ms

上面得出的数据表明通过 ID 进行搜索比通过 CLASS 进行搜索快得多。这如何影响到 jQuery 代码?在编写搜索时,您要记住这些技巧:如果既可选择 CLASS 又可选择 ID,那么通常要选择 ID。如果需要在您的代码中搜索某些元素,一定要给它们分配 ID。

 

当然 这只是对于单一的元素来讲。如果你需要选择多个元素,这必然会涉及到 DOM遍历和循环.为了提高性能,建议用for代替each .原生函数总是比辅助组件更快。如果遇到需要遍历对象的情况(如从远程接收的JSON对象),你最好重写 你的(JSON)对象为一个数组,数组的循环处理要容易些。

下面是测试代码:

<script type="text/javascript">
	$(function() {
	var array = new Array ();
       for (var i=0; i<10000; i++) {
           array[i] = i;
       }
	var startTime =  new Date();
	 var l = array.length;
	var str = "";
         for(var j = 0; j < l; j++){
            str += array[j];  
        }
        //$.each(array, function(i, field) {
		//str += field.value;
		//})

	var endTime = new Date();
	alert(endTime - startTime);
	});
	</script>

 对for循环多次测试结果如下:firefox3.5.8:  3ms   IE8:15ms

 对each多次测试结果如下: firefox3.5.8:  30ms     IE8:30ms

 

4.给选择器指定前后文( 提供尽可能多的搜索信息)

   jQuery的参考文档里说:

   传递给jQuery() 原始DOM节点的前后文(如果没有东西被传递,则前后文为整个文档)。

目的是连同选择器一起,实现更为准确的查询。

    所以,如果你一定要利用class来指定目标,至少为选择器指定上下文,以免jQuery费精力去遍历整个DOM文档.

在jQuery中第二快的选择器是tag(标签)选择器( 比如:$("head") )。 ,因为它来自原生getElementsByTagName() 方法。考虑到底层 JavaScript 代码之后,这就不足为奇了。通过提供元素标记,与 CLASS 参数匹配的搜索元素数量将大大减少,从而将搜索性能提升至与本例中的 ID 搜索相当。开发人员在编写 jQuery 选择方法时不能偷懒,尽管 jQuery 的简单让人产生偷懒的欲望。简单让您放松了警惕。搜索机制变得如此简单,让我们倾向于仅输入一条信息。然而,您应该总是尽可能多地输入信息,尤其是已知信息。

  继续看刚才那段HTML代码.

  比如需要选择 红绿 单选框,
那么可以使用一个tag name来限制(修饰)class , (并且不要忘记就近的ID):如下所示:

var active_light = $(‘#traffic_light input.on’); 

 注意: 在jquery中Class是最慢的选择器. IE浏览器下它会遍历所有DOM节点不管它用在那里. tag.class 的方式 在IE下的性能  好于 .class 方式。 但在Firefox下  却低于 直接 .class方式。 Google浏览器下两种都差不多。

在使用tag来修饰class的时候,我们需要注意以下几点:

(1) 不要使用tag来修饰ID ,如下所示:

var content = $("div#content");

 这样一来,选择器会先遍历所有的div元素,然后匹配#content。

下面是我的测试结果:

测试Htm代码如下所示,我复制了很多遍div标签:

<div class="demo" id="demo">
<div >
<form method="post" action="#">
<h2>交通信号灯</h2>
</form>
</div>
<div id="content">
<form method="post" action="#">
<h2>交通信号灯</h2>
<ul id="traffic_light">
<li><input type="radio" class="on" name="light" value="red" /> 红色</li>
<li><input type="radio" class="off" name="light" value="yellow" /> 黄色</li>
<li><input type="radio" class="off" name="light" value="green" /> 绿色</li>
</ul>
<input class="button" id="traffic_button" type="submit" value="Go" />
</form>
</div>
<div >
<form method="post" action="#">
<h2>交通信号灯</h2>
<ul id="traffic_light">
<li><input type="radio" class="on" name="light" value="red" /> 红色</li>
<li><input type="radio" class="off" name="light" value="yellow" /> 黄色</li>
<li><input type="radio" class="off" name="light" value="green" /> 绿色</li>
</ul>
<input class="button" id="traffic_button1" type="submit" value="Go" />
</form>
</div>
<div >
<form method="post" action="#">
<h2>交通信号灯</h2>
</form>
</div>
<div >
<form method="post" action="#">
<h2>交通信号灯</h2>
</form>
</div>
<div >
<form method="post" action="#">
<h2>交通信号灯</h2>
</form>
</div>
</div><!-- End demo-description -->

 JS代码如下所示:

<script type="text/javascript">
	$(function() {
	var startTime =  new Date();
	for(var i = 0; i < 10000; i++){
           var content = $("div#content");
	    //var content = $("#content");
	}
		var endTime = new Date();
		alert(endTime - startTime);
	});
	</script>

 对第一种选择器多次测试结果如下:firefox3.5.8:  610ms   IE8:1650ms

 对第二种选择器多次测试结果如下: firefox3.5.8:  175ms     IE8:1220ms

(2)用ID修饰ID也是画蛇添足:,如下所示:

  var content = $("#content #traffic_button");

下面进行测试:

测试的HTML代码还是上面的那一段代码.js代码如下所示:

<script type="text/javascript">
	$(function() {
	var startTime =  new Date();
	for(var i = 0; i < 10000; i++){
	    var content = $("#traffic_button");
	    //var content = $("#content #traffic_button");
	}
		var endTime = new Date();
		alert(endTime - startTime);
	});
	</script>

 对第一种选择器多次测试结果如下:firefox3.5.8:  185ms   IE8:1205ms

 对第二种选择器多次测试结果如下: firefox3.5.8:  655ms     IE8:1650ms

从上面的测试结果可看出:用ID修饰ID进行选择时,基本不会使查找元素过程效率提高,反而可以降低.

 

(3 )如果使用属性选择器,也请尽量使用tag来修饰,如下所示:

$('p[row="c3221"]').html();而不是这样:$('[row="c3221"]').html();

 

 

从上面的测试结果来看,影响javascript(jquery)性能的,除了代码本身外,另一个重要方面是用于运行 JavaScript 的浏览器.每个浏览器内部都包含一个 JavaScript 引擎,即用于解析和执行 JavaScript 代码并处理 Web 应用程序页面的本机代码。因此,JavaScript 的性能严重依赖于客户端使用的浏览器.据有经验的人进行过测试得出的结果是:浏览器对性能的影响是 JavaScript 库的 9 倍。 还有一个重要的结论就是:google的浏览器Chrome是最快的JavaScript 引擎.Firefox和 Safari次之,而IE(特别是IE6,那解析速度)则是最慢JavaScript 引擎.

 

评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值