jQuery代码优化 遍历篇


Posted in Javascript onNovember 01, 2011

了解了jQuery对DOM进行遍历背后的工作机制,可以在编写代码时有意识地避免一些不必要的重复操作,从而提升代码的性能。本文就从jQuery的遍历机制入手简单探讨一下优化jQuery代码的问题。

jQuery对象栈

jQuery内部维护着一个jQuery对象栈。每个遍历方法都会找到一组新元素(一个jQuery对象),然后jQuery会把这组元素推入到栈中。而每个jQuery对象都有三个属性:context、selector和prevObject,其中的prevObject属性就指向这个对象栈中的前一个对象,而通过这个属性可以回溯到最初的DOM元素集。

jQuery为我们操作这个内部对象栈提供了两个非常有用的方法:

.end()
.andSelf()
调用第一个方法只是简单地弹出一个对象(结果就是回到前一个jQuery对象)。第二个方法更有意思,调用它会在栈中回溯一个位置,然后把两个位置上的元素集组合起来,并把这个新的、组合之后的元素集推入栈的上方。

利用这个DOM元素栈可以减少重复的查询和遍历的操作,而减少重复操作也正是优化jQuery代码性能的关键所在。

优化示例
下面是一个函数(省略了前后代码),用于实现表格行条纹效果:

function stripe() { 
$('#news').find('tr.alt').removeClass('alt'); 
$('#news tbody').each(function() { 
$(this).children(':visible').has('td') 
.filter(':group(3)').addClass('alt'); 
}); 
}

stripe()函数两次使用了ID选择符#news查找元素:一次是为了从带有alt类的行中删除该类,另一次是为了给新选中的行添加这个类。

优化这个函数的方法有两个,一是连缀。

连缀
连缀优化利用的就是jQuery的内部对象栈和.end()方法。优化后的代码如下:

function stripe() { 
$('#news'). 
find('tr.alt').removeClass('alt').end() 
find('tbody').each(function() { 
$(this).children(':visible').has('td') 
.filter(':group(3)').addClass('alt'); 
}); 
}

第一次调用.find()会把表格行推到栈上,然后的.end()方法则把这些行弹出,从而让下一次调用.find()仍然是在#news表格上执行操作。这样就把两次选择符查找减少为一次。

另一个优化方法是缓存。

缓存
所谓缓存,在这里就是把之前操作的结果保存起来,以便将来重用。优化后的代码如下:

var $news = $('#news'); 
function stripe() { 
$news.find('tr.alt').removeClass('alt'); 
$news.find('tbody').each(function() { 
$(this).children(':visible').has('td') 
.filter(':group(3)').addClass('alt'); 
}); 
}

与连缀的方法相比,缓存方式稍嫌冗长,因为额外创建了一个用于保存jQuery对象的变量。但从另一个角度来看,这种方式在代码中可以实现对选中元素的两次操作完全分离,而这也许可以满足我们其他情况下的需求。同样,因为可以把选中的元素保存在stripe()函数之外,也就避免了每次调用函数时重复查询选择符的操作。

结论
利用jQuery的内部对象栈和缓存,可以减少重复的DOM查询及遍历,从而提高脚本执行速度。

因为根据ID在页面中选择元素速度极快,以上两个例子在优化前后不会有明显的性能差异。在实际编码中,应该选择可读性最好、最容易维护的方式。如果真的遇到了性能瓶颈,以上优化技术都可以起到立竿见影的效果。

(注:本文基于《jQuery基础教程(第3版)》相关章节内容编撰而成。)

Javascript 相关文章推荐
getElementsByTagName vs selectNodes效率 及兼容的selectNodes实现
Feb 26 Javascript
百度Popup.js弹出框进化版 拖拽小框架发布 兼容IE6/7/8,Firefox,Chrome
Apr 13 Javascript
Jquery跨域获得Json时invalid label错误的解决办法
Jan 11 Javascript
jquery实现图片左右间隔滚动特效(可自动播放)
May 08 Javascript
浅谈Javascript中深复制
Dec 01 Javascript
node.js中的console.log方法使用说明
Dec 09 Javascript
jQuery中removeAttr()方法用法实例
Jan 05 Javascript
以BootStrap Tab为例写一个前端组件
Jul 25 Javascript
基于vue打包后字体和图片资源失效问题的解决方法
Mar 06 Javascript
Vue.js 中 axios 跨域访问错误问题及解决方法
Nov 21 Javascript
在Vue项目中引入JQuery-ui插件的讲解
Jan 27 jQuery
js实现坦克移动小游戏
Oct 28 Javascript
jQuery代码优化 选择符篇
Nov 01 #Javascript
jQuery代码优化之基本事件
Nov 01 #Javascript
js下获得客户端操作系统的函数代码(1:vista,2:windows7,3:2000,4:xp,5:2003,6:2008)
Oct 31 #Javascript
线路分流自动智能跳转代码,自动选择最快镜像网站(js)
Oct 31 #Javascript
IE与Firefox在JavaScript上的7个不同句法分享
Oct 30 #Javascript
加载 Javascript 最佳实践
Oct 30 #Javascript
js判断是否为数组的函数: isArray()
Oct 30 #Javascript
You might like
zend api扩展的php对象的autoload工具
2011/04/18 PHP
关于PHP模板Smarty的初级使用方法以及心得分享
2013/06/21 PHP
php根据isbn书号查询amazon网站上的图书信息的示例
2014/02/13 PHP
php对称加密算法示例
2014/05/07 PHP
php使用fopen创建utf8编码文件的方法
2014/10/31 PHP
php限制上传文件类型并保存上传文件的方法
2015/03/13 PHP
浅谈laravel框架sql中groupBy之后排序的问题
2019/10/17 PHP
获取页面高度,窗口高度,滚动条高度等参数值getPageSize,getPageScroll
2006/09/22 Javascript
JS增加行复制行删除行的实现代码
2013/11/09 Javascript
$("").click与onclick的区别示例介绍
2014/09/25 Javascript
jQuery使用元素属性attr赋值详解
2015/02/27 Javascript
JavaScript中的getTimezoneOffset()方法使用详解
2015/06/10 Javascript
Nodejs学习item【入门手上】
2016/05/05 NodeJs
滚动条的监听与内容随着滚动条动态加载的实现
2017/02/08 Javascript
mpvue构建小程序的方法(步骤+地址)
2018/05/22 Javascript
微信小程序支付PHP代码
2018/08/23 Javascript
Vue实现商品详情页的评价列表功能
2019/09/04 Javascript
vue与iframe之间的信息交互的实现
2020/04/08 Javascript
解决vuecli3中img src 的引入问题
2020/08/04 Javascript
vue-admin-template配置快捷导航的代码(标签导航栏)
2020/09/04 Javascript
解决python3捕获cx_oracle抛出的异常错误问题
2018/10/18 Python
pycharm中使用anaconda部署python环境的方法步骤
2018/12/19 Python
我就是这样学习Python中的列表
2019/06/02 Python
python制作英语翻译小工具代码实例
2019/09/09 Python
Python字典常见操作实例小结【定义、添加、删除、遍历】
2019/10/25 Python
Python openpyxl模块原理及用法解析
2020/01/19 Python
使用python自动追踪你的快递(物流推送邮箱)
2020/03/17 Python
惠普美国官方商店:HP Official Store
2016/08/28 全球购物
Silk Therapeutics官网:清洁、抗衰老护肤品
2020/08/12 全球购物
恶意软件的定义
2014/11/12 面试题
JAVA程序员面试题
2012/10/03 面试题
实习教师自我鉴定
2013/12/12 职场文书
酒店个人求职信范文
2014/01/25 职场文书
六五普法宣传标语
2014/10/06 职场文书
幼儿园亲子活动感想
2015/08/07 职场文书
使用Python开发冰球小游戏
2022/04/30 Python