JQuery 1.10.2源码分析学习3

来源:互联网 发布:魔兽世界战士知乎 编辑:程序博客网 时间:2024/06/05 12:47

今天主要接着上一篇来讲讲jQuery.prototype中的一些方法,闲话不多说,直接开始。

  1.    toArray: function() {  
  2.         return core_slice.call( this );  
  3.     }


toArray: 把JQuery集合中所有DOM元素恢复成一个数组。

从源码中可以看出toArray() 返回调用了 core_slice.call( this );在jquery源码中我找到这么两段

// List of deleted data cache ids, so we can reuse them
core_deletedIds = [],

core_slice = core_deletedIds.slice,


slice: function() {
return this.pushStack( core_slice.apply( this, arguments ) );
},

从上面可以看出core_deletedIds 是个数组,core_slice.apply( this, arguments )实现了把对象里的属性放到core_deletedIds数组中这样实现了对象转成数组。

其实大家想说了为什么调core_slice时为什么不用call,而用了apply。而在toArray中调用中使用了call。

先看下这2个的定义吧。

call方法: 
语法:call([thisObj[,arg1[, arg2[,   [,.argN]]]]]) 
定义:调用一个对象的一个方法,以另一个对象替换当前对象。 
说明: 
call 方法可以用来代替另一个对象调用一个方法。call 方法可将一个函数的对象上下文从初始的上下文改变为由 thisObj 指定的新对象。 
如果没有提供 thisObj 参数,那么 Global 对象被用作 thisObj。 

apply方法: 
语法:apply([thisObj[,argArray]]) 
定义:应用某一对象的一个方法,用另一个对象替换当前对象。 
说明: 
如果 argArray 不是一个有效的数组或者不是 arguments 对象,那么将导致一个 TypeError。 
如果没有提供 argArray 和 thisObj 任何一个参数,那么 Global 对象将被用作 thisObj, 并且无法被传递任何参数。

他们的区别在于:

对于apply和call两者在作用上是相同的,但两者在参数上有区别的。
对于第一个参数意义都一样,但对第二个参数:
apply传入的是一个参数数组,也就是将多个参数组合成为一个数组传入,而call则作为call的参数传入(从第二个参数开始)。

如 func.call(func1,var1,var2,var3)对应的apply写法为:func.apply(func1,[var1,var2,var3])
同时使用apply的好处是可以直接将当前函数的arguments对象作为apply的第二个参数传入。


  1.  // Take an array of elements and push it onto the stack  
  2.     // (returning the new matched element set)  
  3.     pushStackfunction( elems ) {  
  4.   
  5.         // Build a new jQuery matched element set  
  6.         var ret = jQuery.merge( this.constructor(), elems );  
  7.   
  8.         // Add the old object onto the stack (as a reference)  
  9.         ret.prevObject = this;  
  10.         ret.context = this.context;  
  11.   
  12.         // Return the newly-formed element set  
  13.         return ret;  
  14.     },  

  

pushStack:取一个数组中的元素,将其放入堆上,返回新的堆上的元素集合(jQuery对象)

在jQuery内部,pushStack()方法通过改变一个jQuery对象的prevObject属性来"跟踪"链式调用中前一个方法返回的DOM结果集(被jQuery封装过,也是个jQuery对象,说是"跟踪",是因为实际存储的是个引用)PS:这是在网上找到的一段解释。

从源码中可以看出pushStack这个方法接受参数‘数组’,接着jQuery.merge( this.constructor(), elems ),merge的作用就是合并2个数组。

  1. ret.prevObject = this;  
  2.         ret.context = this.context;  
这2句的作用就是 将上个对象的引用推入栈中。

ret.prevObject = this;这句话很重要在end中也有用到。

最后返回最新的Jquery对象。

  1. end: function() {  
  2.         return this.prevObject || this.constructor(null);  
  3.     },


end:大多数 jQuery 的遍历方法会操作一个 jQuery 对象实例,并生成一个匹配不同 DOM 元素集的新对象。当发生这种情况时,应该会把新的元素集推入维持在对象中的堆栈内。每次成功的筛选方法调用都会把新元素推入堆栈中。如果我们需要老的元素集,可以使用 end() 从堆栈中弹出新集合。

实例

选择所有段落,找到这些段落中的 span 元素,然后将它们恢复为段落,并把段落设置为两像素的红色边框:

$("p").find("span").end().css("border", "2px red solid");

上面的例子就说明了end的实际语法也更好理解。

  1. // Get the Nth element in the matched element set OR  
  2.     // Get the whole matched element set as a clean array  
  3.     get: function( num ) {  
  4.         return num == null ?  
  5.   
  6.             // Return a 'clean' array  
  7.             this.toArray() :  
  8.   
  9.             // Return just the object  
  10.             ( num < 0 ? thisthis.length + num ] : this[ num ] );  
  11.     },  
  1. eq: function( i ) {  
  2.         var len = this.length,  
  3.             j = +i + ( i < 0 ? len : 0 );  
  4.         return this.pushStack( j >= 0 && j < len ? [ this[j] ] : [] );  
  5.     },  

get:说到get需要把它和eq一起来说  eq返回的是一个jquery对象(这个用了pushStack),get返回的是一个html 对象数组(这个用了toArray)。

看上面get和eq的源码就可以看出来了get调用了toArray() eq调用了pushStack()。其实通过上面对toArray()的解释就可以知道toArray()中也调用了pushStack()。只是get多做了一步,把对象转成数组。


  1.  first: function() {  
  2.         return this.eq( 0 );  
  3.     },  
  4.   
  5.     last: function() {  
  6.         return this.eq( -1 );  
  7.     },  

frist:选取匹配好的元素集合中的第一个元素。

last:选取匹配好的元素集合中的最后一个元素。

上面对frist和last的源码一看就能知道他们都是调用了eq()得到了了一个对象中的一个元素。

  1.  map: function( callback ) {  
  2.         return this.pushStack( jQuery.map(thisfunction( elem, i ) {  
  3.             return callback.call( elem, i, elem );  
  4.         }));  
  5.     }, 
map: 把每个元素通过函数传递到当前匹配集合中,生成包含返回值的新的 jQuery 对象。

这个感觉也不要做过多的解释直接看源码相信大家就能看明白吧。

通过上面的讲解就可以发现其实这些方法中用到最多的就是pushStack了。

原创粉丝点击