jQuery中的pushStack实现原理和应用实例


Posted in Javascript onFebruary 03, 2015

pushStack是jQuery内核中一个非常重要的函数,它是如此重要,以至于许多jQuery内部函数中都频繁用到它。平常情况下,虽然很少用到它, 但是掌握这个函数,不仅有利于理解jQuery的运行原理,还方便我们做更加高级的jQuery操作。

顾名思义,pushStack是入栈, 栈作为一种数据结构,是一种只能在一端进行插入和删除操作的特殊线性表。数据入栈时,类似与我们进电梯,后进而先出, 如下图:

jQuery中的pushStack实现原理和应用实例

jQuery中的栈其实并不是真正的栈,而是给jQuery对象附加一个属性,指向当前对象的上一个对象, 通过end方法就能返回上一个元素。如下:

<span>1</span>
<span>2</span>
<span>3</span>
<script>
$('span').eq(0).css('fontSize','20px').end().fadeOut(2000);
</script>

上面的代码会使第一个span的字体大小为20px,并让所有span在2秒钟之内fadaout。

pushStack属于jQuery的实例方法,通过jQuery对象调用,如通过$().pushStack(document.getElementsByTagName(‘div')).css(‘background','blue')把所有div的背景都设置为蓝色。那么pushStack的原理是什么,为什么传入的DOM对象可以用css方法操作呢?先来看一下jQuery中pushStack的源码:

pushStack: function( elems ) {
 // Build a new jQuery matched element set
 var ret = jQuery.merge( this.constructor(), elems );
 // Add the old object onto the stack (as a reference)
 ret.prevObject = this;
 ret.context = this.context;
 // Return the newly-formed element set
 return ret;
}
//jQuery.merge
merge: function( first, second ) {
 var l = second.length,
 i = first.length,
 j = 0;
 if ( typeof l === "number" ) {
 for ( ; j < l; j++ ) {
  first[ i++ ] = second[ j ];
 }
 } else {
 while ( second[j] !== undefined ) {
  first[ i++ ] = second[ j++ ];
 }
 }
 first.length = i;
 return first;
}

pushStack的实现比较简单,主要涉及到jQuery的静态方法merge, 这个方法用来合并对象, 设计思路是在第一个对象的基础上,把第二个对象的属性(0至n)附加上去, 理解这一点很重要。再回到pushStack这个函数,首先定义一个局部变量ret存储合并对象,然后给这个对象存储prevObject和context属性,最后返回合并之后的ret对象。这里有几点需要注意:
1, this.constructor 就是jQuery的构造函数init,所以this.constructor()返回一个jQuery对象.
2, 由于jQuery merge函数返回的对象是第二个函数附加到第一个上面,所以ret也是一个jQuery对象,这里可以解释为什么pushStack出入的DOM对象也可以用CSS方法进行操作。
3, 返回的对象的prevObject属性指向上一个对象,所以可以通过这个属性找到栈的上一个对象.

Javascript 相关文章推荐
javascript获取浏览器类型和版本的方法(js获取浏览器版本)
Mar 13 Javascript
JavaScript中双叹号(!!)作用示例介绍
Apr 10 Javascript
jQuery插件制作之参数用法实例分析
Jun 01 Javascript
详解JavaScript操作HTML DOM的基本方式
Oct 21 Javascript
浅谈jquery中的each方法$.each、this.each、$.fn.each
Jun 23 Javascript
Javascript 动态改变imput type属性
Nov 01 Javascript
bootstrap table配置参数例子
Jan 05 Javascript
微信小程序开发(一) 微信登录流程详解
Jan 11 Javascript
微信小程序之获取当前位置经纬度以及地图显示详解
May 09 Javascript
gulp安装以及打包合并的方法教程
Nov 19 Javascript
vue-cli脚手架的安装教程图解
Sep 02 Javascript
JS中DOM元素的attribute与property属性示例详解
Sep 04 Javascript
JavaScript闭包详解
Feb 02 #Javascript
js实现浏览器窗口大小被改变时触发事件的方法
Feb 02 #Javascript
javascript的switch用法注意事项分析
Feb 02 #Javascript
jQuery实现长按按钮触发事件的方法
Feb 02 #Javascript
jQuery实现跟随鼠标运动图层效果的方法
Feb 02 #Javascript
JavaScript针对网页节点的增删改查用法实例
Feb 02 #Javascript
jQuery通过控制节点实现仅在前台通过get方法完成参数传递
Feb 02 #Javascript
You might like
php echo()和print()、require()和include()函数区别说明
2010/03/27 PHP
编写安全 PHP应用程序的七个习惯深入分析
2013/06/08 PHP
ThinkPHP中调用PHPExcel的实现代码
2017/04/08 PHP
JavaScript实现彩虹文字效果的方法
2015/04/16 Javascript
jQuery实现折叠、展开的菜单组效果代码
2015/09/16 Javascript
jQuery+PHP星级评分实现方法
2015/10/02 Javascript
js实现有过渡渐变效果的图片轮播相册(兼容IE,ff)
2016/01/19 Javascript
微信小程序 Record API详解及实例代码
2016/09/30 Javascript
jQuery ajax 当async为false时解决同步操作失败的问题
2016/11/18 Javascript
jQuery窗口拖动功能的实现代码
2017/02/04 Javascript
基于 Vue.js 2.0 酷炫自适应背景视频登录页面实现方式
2018/01/17 Javascript
详解Vue组件之作用域插槽
2018/11/22 Javascript
vue Cli 环境删除与重装教程 - 版本文档
2020/09/11 Javascript
[54:45]2018DOTA2亚洲邀请赛 4.1 小组赛 A组 Optic vs OG
2018/04/02 DOTA
[36:20]完美世界DOTA2联赛PWL S3 access vs Rebirth 第一场 12.17
2020/12/18 DOTA
Python中实现从目录中过滤出指定文件类型的文件
2015/02/02 Python
python 类的继承 实例方法.静态方法.类方法的代码解析
2019/08/23 Python
Python实现串口通信(pyserial)过程解析
2019/09/25 Python
Python导入父文件夹中模块并读取当前文件夹内的资源
2020/11/19 Python
HTML5验证以及日期显示的实现详解
2013/07/05 HTML / CSS
加拿大女鞋品牌:ALDO
2016/11/13 全球购物
德国最大的设计师鞋网上商店:Budapester
2017/12/07 全球购物
施华洛世奇日本官网:SWAROVSKI日本
2018/05/04 全球购物
土耳其玩具商店:Toyzz Shop
2019/08/02 全球购物
关于是否需要写商业计划书
2014/02/07 职场文书
火车的故事教学反思
2014/02/11 职场文书
高中竞选班长演讲稿
2014/04/24 职场文书
2014年“世界无车日”活动方案
2014/09/21 职场文书
党员示范岗材料
2014/12/19 职场文书
MySQL主从复制断开的常用修复方法
2021/04/07 MySQL
详解vue身份认证管理和租户管理
2021/05/25 Vue.js
Python还能这么玩之只用30行代码从excel提取个人值班表
2021/06/05 Python
浅谈MySQL next-key lock 加锁范围
2021/06/07 MySQL
Vue实现tab导航栏并支持左右滑动功能
2021/06/28 Vue.js
python 管理系统实现mysql交互的示例代码
2021/12/06 Python
Vue router配置与使用分析讲解
2022/12/24 Vue.js