作者:yanyige | 发布时间:2017-03-09 13:07
接上次,谈到了jQuery中构造函数中的几个方法
2.7.3 .get( [index] )
方法.get( [index] ) 返回当前jQuery 对象中指定位置的元素或包含了全部元素的数组。 如果没有传入参数,则调用.toArray() 返回包含了所有元素的数组;如果指定了参数index, 则返回一个单独的元素;参数index 从0 开始计算,并且支持负数,负数表示从元素集合末 尾开始计算。相关代码如下所示:
227 // Get the Nth element in the matched element set OR
228 // Get the whole matched element set as a clean array
229 get: function( num ) {
230 return num == null ?
231
232 // Return a 'clean' array
233 this.toArray() :
234
235 // Return just the object
236 ( num < 0 ? this[ this.length + num ] : this[ num ] );
237 },
2.7.3 .each( function(index, Element) )、jQuery.each( collection, callback(indexInArray, valueOfElement) )
1. .each( function(index, Element) )
方法.each() 遍历当前jQuery 对象,并在每个元素上执行回调函数。每当回调函数执行时,会 传递当前循环次数作为参数,循环次数从0 开始计数;更重要的是,回调函数是在当前元素为上 下文的语境中触发的,即关键字this 总是指向当前元素;在回调函数中返回false 可以终止遍历。 方法.each() 内部通过简单的调用静态方法jQuery.each() 实现,相关代码如下所示:
267 // Execute a callback for every element in the matched set.
268 // (You can seed the arguments with an array of args, but this is
269 // only used internally.)
270 each: function( callback, args ) {
271 return jQuery.each( this, callback, args );
272 },
2. jQuery.each( collection, callback(indexInArray, valueOfElement) )
静态方法jQuery.each() 是一个通用的遍历迭代方法,用于无缝地遍历对象和数组。对于 数组和含有length 属性的类数组对象(如函数参数对象arguments),该方法通过下标遍历, 从0 到length-1 ;对于其他对象则通过属性名遍历(for-in)。在遍历过程中,如果回调函数 返回false,则结束遍历。相关代码如下所示:
627 // args is for internal usage only
628 each: function( object, callback, args ) {
629 var name, i = 0,
630 length = object.length,
631 isObj = length === undefined || jQuery.isFunction( object );
632
633 if ( args ) {
634 if ( isObj ) {
635 for ( name in object ) {
636 if ( callback.apply( object[ name ], args ) === false ) {
637 break;
638 }
639 }
640 } else {
641 for ( ; i < length; ) {
642 if ( callback.apply( object[ i++ ], args ) === false ) {
643 break;
644 }
645 }
646 }
647
648 // A special, fast, case for the most common use of each
649 } else {
650 if ( isObj ) {
651 for ( name in object ) {
652 if ( callback.call( object[ name ], name, object[ name ])===false){
653 break;
654 }
655 }
656 } else {
657 for ( ; i < length; ) {
658 if ( callback.call( object[ i ], i, object[ i++ ] ) === false ) {
659 break;
660 }
661 }
662 }
663 }
664
665 return object;
666 },
2.7.4 .map( callback(index, domElement) )、jQuery.map( arrayOrObject,callback(value, indexOrKey) )
1. .map( callback(index, domElement) )
方法.map() 遍历当前jQuery对象,在每个元素上执行回调函数,并将回调函数的返回值放入一个新jQuery 对象中。该方法常用于获取或设置DOM 元素集合的值。执行回调函数时,关键字this 指向当前元素。回调函数可以返回一个独立的数据项或数据项数组,返回值将被插入结果集中;如果返回一个数组,数组中的元素会被插入结果集;如果回调函数返回null或undefined,则不会插入任何元素。方法.map() 内部通过静态方法jQuery.map()和原型方法.pushStack()实现,相关代码如 下所示:
304 map: function( callback ) {
305 return this.pushStack( jQuery.map(this, function( elem, i ) {
306 return callback.call( elem, i, elem );
307 }));
308 },
2. jQuery.map( arrayOrObject, callback(value, indexOrKey) )
静态方法jQuery.map() 对数组中的每个元素或对象的每个属性调用一个回调函数,并将回调函数的返回值放入一个新的数组中。执行回调函数时传入两个参数:数组元素或属性值,元素下标或属性名。关键字this 指向全局对象window。回调函数的返回值会被放入新的数组中;如果返回一个数组,数组中将被扁平化后插入结果集;如果返回null或undefined,则不会放入任何元素。相关代码如下所示:
760 // arg is for internal usage only
761 map: function( elems, callback, arg ) {
762 var value, key, ret = [],
763 i = 0,
764 length = elems.length,
765 // jquery objects are treated as arrays
766 isArray = elems instanceof jQuery || length !== undefined && typeof length === "number" && ( ( length > 0 && elems[ 0 ] && elems[ length -1 ] ) || length === 0 || jQuery.isArray( elems ) ) ;
767
768 // Go through the array, translating each of the items to their
769 if ( isArray ) {
770 for ( ; i < length; i++ ) {
771 value = callback( elems[ i ], i, arg );
772
773 if ( value != null ) {
774 ret[ ret.length ] = value;
775 }
776 }
777
778 // Go through every key on the object,
779 } else {
780 for ( key in elems ) {
781 value = callback( elems[ key ], key, arg );
782
783 if ( value != null ) {
784 ret[ ret.length ] = value;
785 }
786 }
787 }
788
789 // Fl atten any nested arrays
790 return ret.concat.apply( [], ret );
791 },
第790 行:最后在空数组[] 上调用方法concat() 扁平化结果集ret 中的元素,并返回。
2.7.5 .pushStack( elements, name, arguments )
原型方法.pushStack() 创建一个新的空jQuery 对象,然后把DOM 元素集合放入这个jQuery 对象中,并保留对当前jQuery 对象的引用。
原型方法.pushStack() 是核心方法之一,它为以下方法提供支持:
- jQuery 对象遍历:.eq()、.first()、.last()、.slice()、.map()。
- DOM 查找、过滤:.find()、.not()、.filter()、.closest()、.add()、.andSelf()。
- DOM 遍历:.parent()、.parents()、.parentsUntil()、.next()、.prev()、.nextAll() .prevAll()、.nextUnit()、.prevUnit()、.siblings()、.children()、.contents()。
- DOM插入:jQuery.before()、jQuery.after()、jQuery.replaceWith()、.append()、.prepent()、.before()、.after()、.replaceWith()。
相关代码:
239 // Take an array of elements and push it onto the stack
240 // (returning the new matched element set)
241 pushStack: function( elems, name, selector ) {
242 // Build a new jQuery matched element set
243 var ret = this.constructor();
244
245 if ( jQuery.isArray( elems ) ) {
246 push.apply( ret, elems );
247
248 } else {
249 jQuery.merge( ret, elems );
250 }
251
252 // Add the old object onto the stack (as a reference)
253 ret.prevObject = this;
254
255 ret.context = this.context;
256
257 if ( name === "find" ) {
258 ret.selector = this.selector + ( this.selector ? " " : "" ) + selector;
259 } else if ( name ) {
260 ret.selector = this.selector + "." + name + "(" + selector + ")";
261 }
262
263 // Return the newly-formed element set
264 return ret;
265 },
2.7.6 .end()
方法.end() 结束当前链条中最近的筛选操作,并将匹配元素集合还原为之前的状态。相关代码如下所示:
310 end: function() {
311 return this.prevObject || this.constructor(null);
312 },
第311 行:返回前一个jQuery 对象。如果属性prevObject不存在,则构建一个空的jQuery 对象返回。
方法.pushStack() 用于入栈,方法.end() 则用于出栈。这两个方法可以像下面的例子这样使用:
$('ul.first').find('.foo')
.css('background-color', 'red')
.end().find('.bar')
.css('background-color', 'green')
.end();
2.7.7 .eq( index )、.first()、.last()、.slice( start [, end] )
方法.eq( index ) 将匹配元素集合缩减为集合中指定位置的元素;方法.first()将匹配元素集合缩减为集合中的第一个元素;方法.last()将匹配元素集合缩减为集合中的最后一个元素;方法.slice( start [, end] ) 将匹配元素集合缩减为指定范围的子集。方法.first()和.last()通过调用.eq( index ) 实现,.eq( index ) 则通过.slice( start [, end] ) 实现,.slice( start [, end] ) 则通过调用.pushStack( elements, name, arguments ) 实现,方法调用链为.first/last() → .eq( index ) → .slice( start [, end] ) → .pushStack( elements, name, arguments )。
相关代码如下所示:
284 eq: function( i ) {
285 i = +i;
286 return i === -1 ?
287 this.slice( i ) :
288 this.slice( i, i + 1 );
289 },
290
291 first: function() {
292 return this.eq( 0 );
293 },
294
295 last: function() {
296 return this.eq( -1 );
297 },
298
299 slice: function() {
300 return this.pushStack( slice.apply( this, arguments ),
301 "slice", slice.call(arguments).join(",") );
302 },
2.7.8 .push( value, … )、.sort( [orderfunc] )、.splice( start,deleteCount, value, … )
方法.push( value, … ) 向当前jQuery 对象的末尾添加新元素,并返回新长度,例如:
var foo = $(document);
foo.push( document.body ); // 2
方法.sort( [orderfunc] ) 对当前jQuery 对象中的元素进行排序,可以传入一个比较函数 来指定排序方式
方法.splice( start,deleteCount, value, … ) 向当前jQuery 对象中插入、删除或替换元素。
如果从当前jQuery 对象中删除了元素,则返回含有被删除元素的数组。
方法.push()、.sort()、.splice() 仅在内部使用,都指向同名的数组方法,因此它们的参数、 功能和返回值与数组方法完全一致。
2.8 静态属性和方法
在构造jQuery 对象模块中还定义了一些重要的静态属性和方法,它们是其他模块实现的 基础。
整体结构如下:
388 jQuery.extend({
389 noConflict: function( deep ) {},
402 isReady: false,
406 readyWait: 1,
409 holdReady: function( hold ) {},
418 ready: function( wait ) {},
444 bindReady: function() {},
492 isFunction: function( obj ) {},
496 isArray: Array.isArray || function( obj ) {},
501 isWindow: function( obj ) {},
505 isNumeric: function( obj ) {},
509 type: function( obj ) {},
515 isPlainObject: function( obj ) {},
544 isEmptyObject: function( obj ) {},
551 error: function( msg ) {},
555 parseJSON: function( data ) {},
581 parseXML: function( data ) {},
601 noop: function() {},
606 globalEval: function( data ) {},
619 camelCase: function( string ) {},
623 nodeName: function( elem, name ) {},
628 each: function( object, callback, args ) {},
669 trim: trim ? function( text ) {} : function( text ) {},
684 makeArray: function( array, results ) {},
702 inArray: function( elem, array, i ) {},
724 merge: function( first, second ) {},
744 grep: function( elems, callback, inv ) {},
761 map: function( elems, callback, arg ) {},
794 guid: 1,
798 proxy: function( fn, context ) {},
825 access: function( elems, key, value, exec, fn, pass ) { },
852 now: function() {},
858 uaMatch: function( ua ) {},
870 sub: function() {},
891 browser: {}
892 });
2.8.1 jQuery.noConflict( [removeAll] )
方法jQuery.noConflict( [removeAll] ) 用于释放jQuery 对全局变量$ 的控制权,可选的参 数removeAll 指示是否释放对全局变量jQuery 的控制权。$ 仅仅是jQuery 的别名,所有的功 能没有$ 也能使用。 很多JavaScript 库使用美元符$ 作为函数名或变量名,在使用jQuery 的同时,如果需要 使用另一个JavaScript 库,可以调用$.noConflict() 返回$ 给其他库。如果有必要(例如,在 一个页面中使用多个版本的jQuery 库,但很少有这样的必要),也可以释放全局变量jQuery 的控制权,只需要给这个方法传入参数true 即可。
相关代码如下所示:
30 // Map over jQuery in case of overwrite
31 _jQuery = window.jQuery,
32
33 // Map over the $ in case of overwrite
34 _$ = window.$,
388 jQuery.extend({
389 noConflict: function( deep ) {
390 if ( window.$ === jQuery ) {
391 window.$ = _$;
392 }
393
394 if ( deep && window.jQuery === jQuery ) {
395 window.jQuery = _jQuery;
396 }
397
398 return jQuery;
399 },
2.8.2 类型检测:jQuery.isFunction( obj )、jQuery.isArray( obj )、jQuery.isWindow( obj )、jQuery.isNumeric( value )、jQuery.type( obj )、jQuery.isPlainObject( object )、jQuery.isEmptyObject( object )
1. jQuery.isFunction( obj )、jQuery.isArray( obj )
方法jQuery.isFunction( obj ) 用于判断传入的参数是否是函数;方法jQuery.isArray( obj ) 用于判断传入的参数是否是数组。这两个方法的实现依赖于方法jQuery.type( obj ),通过判断 jQuery.type( obj ) 返回值是否是“function”和“array”来实现。相关代码如下所示:
489 // See test/unit/core.js for details concerning isFunction.
490 // Since version 1.3, DOM methods and functions like alert
491 // aren't supported. They return false on IE (#2968).
492 isFunction: function( obj ) {
493 return jQuery.type(obj) === "function";
494 },
495
496 isArray: Array.isArray || function( obj ) {
497 return jQuery.type(obj) === "array";
498 },
499
2. jQuery.type( obj )
方法jQuery.type( obj )用于判断参数的内建JavaScript 类型。如果参数是undefined 或 null,返回“ undefined”或“null”;如果参数是JavaScript内部对象,则返回对应的字符串名称;其他情况一律返回“object”。相关代码如下所示:
509 type: function( obj ) {
510 return obj == null ?
511 String( obj ) :
512 class2type[ toString.call(obj) ] || "object";
513 },
其中class2type的构造方法如下:
87 toString = Object.prototype.toString, 94 // [[Class]] -> type pairs 95 class2type = {}; 894 // Ppulate the class2type map 895 jQuery.each("Boolean Number String Function Array Date RegExp Object".split(" "), function(i, name) { 896 class2type[ "[object " + name + "]" ] = name.toLowerCase(); 897 });
对象class2type 初始化后的结构为:
{
"[object Array]": "array"
"[object Boolean]": "boolean"
"[object Date]": "date"
"[object Function]": "function"
"[object Number]": "number"
"[object Object]": "object"
"[object RegExp]": "regexp"
"[object String]": "string"
}
3. jQuery.isWindow( obj )
方法jQuery.isWindow(obj)用于判断传入的参数是否是window对象,通过检测是否存在特征属性setInterval来实现,相关代码如下所示:
500 // A crude way of determining if an object is a window
501 isWindow: function( obj ) {
502 return obj && typeof obj === "object" && "setInterval" in obj;
503 },
在最新版本中改为是对窗口自身的引用。
4. jQuery.isNumeric( value )
方法jQuery.isNumeric( value ) 用于判断传入的参数是否是数字,或者看起来是否像数字,相关代码如下所示:
505 isNumeric: function( obj ) {
506 return !isNaN( parseFloat(obj) ) && isFinite( obj );
507 },
先执行parseFloat( obj )尝试把参数obj解析为数字,然后用isNaN()判断解析结果是否是合法数字,并用isFinite() 判断参数obj是否是有限的。如果parseFloat(obj)的解析结果是合法数字,并且参数obj是有限数字,则返回true;否则返回false。
5. jQuery.isPlainObject( object )
方法jQuery.isPlainObject(object)用于判断传入的参数是否是“纯粹”的对象,即是否是用对象直接量{} 或new Object() 创建的对象。相关代码如下所示:
515 isPlainObject: function( obj ) {
516 // Must be an Object.
517 // Because of IE, we also have to check the presence of the constructor property.
518 // Make sure that DOM nodes and window objects don't pass through, as well
519 if ( !obj || jQuery.type(obj) !== "object" || obj.nodeType || jQuery.isWindow( obj ) ) {
520 return false;
521 }
522
523 try {
524 // Not own constructor property must be Object
525 if ( obj.constructor &&
526 !hasOwn.call(obj, "constructor") &&
527 !hasOwn.call(obj.constructor.prototype, "isPrototypeOf") ) {
528 return false;
529 }
530 } catch ( e ) {
531 // IE8,9 Will throw exceptions on certain host objects #9897
532 return false;
533 }
534
535 // Own properties are enumerated firstly, so to speed up,
536 // if last one is own, then all properties are own.
537
538 var key;
539 for ( key in obj ) {}
540
541 return key === undefined || hasOwn.call( obj, key );
542 },
第523 ~ 533 行:检查对象obj是否由构造函数Object()创建。如果对象obj满足以下所有条件,则认为不是由构造函数Object() 创建,而是由自定义构造函数创建,返回false:
- 对象 obj 含有属性 constructor。由构造函数创建的对象都有一个 constructor 属性,默 认引用了该对象的构造函数。如果对象obj 没有属性constructor,则说明该对象必然 是通过对象字面量{} 创建的。
- 对象 obj 的属性 constructor 是非继承属性。默认情况下,属性 constructor 继承自构造 函数的原型对象。如果属性constructor是非继承属性,说明该属性已经在自定义构造函数中被覆盖。
- 对象 obj 的原型对象中没有属性 isPrototypeOf。属性 isPrototypeOf 是 Object 原型对象 的特有属性,如果对象obj 的原型对象中没有,说明不是由构造函数Object() 创建, 而是由自定义构造函数创建。
- 执行以上检测时抛出了异常。在 IE8/9中,在某些浏览器对象上执行以上检测时会抛出异常,也应该返回false。
函数hasOwn() 指向Object.prototype.hasOwnProperty( property ),用于检查对象是否含有 执行名称的非继承属性。
6. jQuery.isEmptyObject( object )
方法jQuery.isEmptyObject( object ) 用于检测对象是否是空的(即不包含属性)。例如:
jQuery.isEmptyObject( {} ) // true
jQuery.isEmptyObject( new Object() ) // true
jQuery.isEmptyObject( { foo: "bar" } ) // false
方法jQuery.isEmptyObject( object ) 的相关代码如下所示:
544 isEmptyObject: function( obj ) {
545 for ( var name in obj ) {
546 return false;
547 }
548 return true;
549 },
2.8.3 解析JSON 和XML:jQuery.parseJSON( data )、jQuery.parseXML( data )
1. jQuery.parseJSON( data )
方法jQuery.parseJSON( data )接受一个格式良好的JSON字符串,返回解析后的JavaScript对象。如果传入残缺的JSON字符串可能导致程序抛出异常;如果不传入参数,或者传入空字符串、null、undefined,则返回null。如果浏览器提供了原生方法JSON.parse(),则使用该方法解析JSON 字符串;否则使用( new Function( “return”+ data ) )() 解析JSON 字符串。
代码如下所示:
555 parseJSON: function( data ) {
556 if ( typeof data !== "string" || !data ) {
557 return null;
558 }
559
560 // Make sure leading/trailing whitespace is removed (IE can't handle it)
561 data = jQuery.trim( data );
562
563 // Attempt to parse using the native JSON parser first
564 if ( window.JSON && window.JSON.parse ) {
565 return window.JSON.parse( data );
566 }
567
568 // Make sure the incoming data is actual JSON
569 // Logic borrowed from http:// json.org/json2.js
570 if ( rvalidchars.test( data.replace( rvalidescape, "@" )
571 .replace( rvalidtokens, "]" )
572 .replace( rvalidbraces, "")) ) {
573
574 return ( new Function( "return " + data ) )();
575
576 }
577 jQuery.error( "Invalid JSON: " + data );
578 },
2.8.4 jQuery.globalEval( code )
方法jQuery.globalEval ( code ) 用于在全局作用域中执行JavaScript代码。很多时候我们希望JavaScript代码是在全局作用域中执行,例如,当动态加载并执行JavaScript 代码时。在IE 中,可以调用方法execScript()让JavaScript代码在全局作用域中执行;在其他浏览器中,则需要在一个自调用匿名函数中调用eval()执行JavaScript代码,自调用匿名函数确保了执行环境是全局作用域。
在严格模式中EVAL函数的执行环境是自己的作用域
2.8.5 jQuery.camelCase( string )
方法jQuery.camelCase( string )转换连字符式的字符串为驼峰式,用于CSS模块和数据缓存模块。例如:
jQuery.camelCase( 'background-color' );
// "backgroundColor"
相关代码:
65 // Matches dashed string for camelizing
66 rdashAlpha = /-([a-z]|[0-9])/ig,
67 rmsPrefix = /^-ms-/,
68
69 // Used by jQuery.camelCase as callback to replace()
70 fcamelCase = function( all, letter ) {
71 return ( letter + "" ).toUpperCase();
72 },
617 // Convert dashed to camelCase; used by the css and data modules
618 // Microsoft forgot to hump their vendor prefix (#9572)
619 camelCase: function( string ) {
620 return string.replace( rmsPrefix, "ms-" ).replace( rdashAlpha, fcamelCase );
621 },
2.8.6 jQuery.nodeName( elem, name )
方法jQuery.nodeName( elem, name ) 用于检查DOM元素的节点名称(即属性nodeName)与指定的值是否相等,检查时忽略大小写。
623 nodeName: function( elem, name ) {
624 return elem.nodeName && elem.nodeName.toUpperCase() === name.toUpperCase();
625 },
2.8.7 jQuery.trim( str )
方法jQuery.trim( str ) 用于移除字符串开头和结尾的空白符。如果传入的参数是null或undefined,则返回空字符串;如果传入的参数是对象,则先获取对象的字符串表示,然后移除开头和结尾的空白符,并返回。
43 // Check if a string has a non-whitespace character in it
44 rnotwhite = /\S/,
45
46 // Used for trimming whitespace
47 trimLeft = /^\s+/,
48 trimRight = /\s+$/,
91 trim = String.prototype.trim,
910 // IE doesn't match non-breaking spaces with \s
911 if ( rnotwhite.test( "\xA0" ) ) {
912 trimLeft = /^[\s\xA0]+/;
913 trimRight = /[\s\xA0]+$/;
914 }
668 // Use native String.trim function wherever possible
669 trim: trim ?
670 function( text ) {
671 return text == null ?
672 "" :
673 trim.call( text );
674 } :
675
676 // Otherwise use our own trimming functionality
677 function( text ) {
678 return text == null ?
679 "" :
680 text.toString().replace( trimLeft, "" ).replace( trimRight, "" );
681 },
2.8.8 数组操作方法:jQuery.makeArray( obj )、jQuery.inArray( value, array [, fromIndex] )、jQuery.merge( first, second )、jQuery.grep( array, function(elementOfArray, indexInArray) [, invert] )
1. jQuery.makeArray( obj )
方法jQuery.makeArray( obj )可以将一个类数组对象转换为真正的数组。在jQuery 内部,还可以为方法jQuery.makeArray()传入第二个参数,这样,第一个参数中的元素将被合并入第二个参数,最后会返回第二个参数,此时返回值的类型不一定是真正的数组。
方法jQuery.makeArray( obj ) 的源码如下:
89 push = Array.prototype.push,
683 // results is for internal usage only
684 makeArray: function( array, results ) {
685 var ret = results || [];
686
687 if ( array != null ) {
688 // The window, strings (and functions) also have 'length'
689 // Theaked logic slightly to handle Blackberry 4.7 RegExp issues #6930
690 var type = jQuery.type( array );
691
692 if ( array.length == null
|| type === "string"
|| type === "function"
|| type === "regexp"
|| jQuery.isWindow( array ) ) {
693 push.call( ret, array );
694 } else {
695 jQuery.merge( ret, array );
696 }
697 }
698
699 return ret;
700 },
2. jQuery.inArray( value, array[, fromIndex] )
方法jQuery.inArray( value, array[, fromIndex] ) 在数组中查找指定的元素并返回其下标, 未找到则返回-1。相关代码如下所示:
702 inArray: function( elem, array, i ) {
703 var len;
704
705 if ( array ) {
706 if ( indexOf ) {
707 return indexOf.call( array, elem, i );
708 }
709
710 len = array.length;
711 i = i ? i < 0 ? Math.max( 0, len + i ) : i : 0;
712
713 for ( ; i < len; i++ ) {
714 // Sip accessing in sparse arrays
715 if ( i in array && array[ i ] === elem ) {
716 return i;
717 }
718 }
719 }
720
721 return -1;
722 },
3. jQuery.merge( first, second )
方法jQuery.merge( first, second ) 用于合并两个数组的元素到第一个数组中。事实上,第一个参数可以是数组或类数组对象,即必须含有整型(或可以转换为整型)属性length;第二个参数则可以是数组、类数组对象或任何含有连续整型属性的对象。
方法jQuery.merge() 的合并行为是破坏性的,将第二个数组中的元素添加到第一个数组 中后,第一个数组就被改变了。如果希望原来的第一个数组不被改变,可以在调用jQuery. merge() 之前创建一份第一个数组的副本:
var newArray = $.merge([], oldArray);
方法jQuery.merge( first, second ) 的相关代码如下所示:
724 merge: function( first, second ) {
725 var i = first.length,
726 j = 0;
727
728 if ( typeof second.length === "number" ) {
729 for ( var l = second.length; j < l; j++ ) {
730 first[ i++ ] = second[ j ];
731 }
732
733 } else {
734 while ( second[j] !== undefined ) {
735 first[ i++ ] = second[ j++ ];
736 }
737 }
738
739 first.length = i;
740
741 return first;
742 },
4. jQuery.grep( array, function( elementOfArray, indexInArray )[, invert] )
方法jQuery.grep( array, function( elementOfArray, indexInArray )[, invert] ) 用于查找数组中满足过滤函数的元素,原数组不会受影响。
如果参数invert 未传入或是false,元素只有在过滤函数返回true,或者返回值可以转换为true时,才会被保存在最终的结果数组中,即返回一个满足回调函数的元素数组;如果参数invert是true,则情况正好相反,返回的是一个不满足回调函数的元素数组。 代码如下所示:
``` 744 grep: function( elems, callback, inv ) { 745 var ret = [], retVal; 746 inv = !!inv; 747 748 // Go through the array, only saving the items 749 // that pass the validator function 750 for ( var i = 0, length = elems.length; i < length; i++ ) { 751 retVal = !!callback( elems[ i ], i ); 752 if ( inv !== retVal ) { 753 ret.push( elems[ i ] ); 754 } 755 } 756 757 return ret; 758 },