jQuery.extend()源码解读

// extend方法为jQuery对象和init对象的prototype扩展方法
// 同时具备独立的扩展普通对象的功能
jQuery.extend = jQuery.fn.extend = function() {
  /*
  *target被扩展的对象
  *length参数的数量
  *deep是否深度操做
  */
  var options, name, src, copy, copyIsArray, clone,
    target = arguments[0] || {},
    i = 1,
    length = arguments.length,
    deep = false;html

  // target为第一个参数,若是第一个参数是Boolean类型的值,则把target赋值给deep
  // deep表示是否进行深层面的复制,当为true时,进行深度复制,不然只进行第一层扩展
  // 而后把第二个参数赋值给target
  if ( typeof target === "boolean" ) {
    deep = target;
    target = arguments[1] || {};数组

    // 将i赋值为2,跳过前两个参数
    i = 2;
  }函数

  // target既不是对象也不是函数则把target设置为空对象。
  if ( typeof target !== "object" && !jQuery.isFunction(target) ) {
    target = {};
  }post

  // 若是只有一个参数,则把jQuery对象赋值给target,即扩展到jQuery对象上
  if ( length === i ) {
    target = this;this

    // i减1,指向被扩展对象
    --i;
  }prototype

  // 开始遍历须要被扩展到target上的参数htm

  for ( ; i < length; i++ ) {
    // 处理第i个被扩展的对象,即除去deep和target以外的对象
    if ( (options = arguments[ i ]) != null ) {
      // 遍历第i个对象的全部可遍历的属性
      for ( name in options ) {
        // 根据被扩展对象的键得到目标对象相应值,并赋值给src
        src = target[ name ];
        // 获得被扩展对象的值
        copy = options[ name ];对象

        // 这里为何是比较target和copy?不该该是比较src和copy吗?
        if ( target === copy ) {
          continue;
        }blog

        // 当用户想要深度操做时,递归合并
        // copy是纯对象或者是数组
        if ( deep && copy && ( jQuery.isPlainObject(copy) || (copyIsArray = jQuery.isArray(copy)) ) ) {
          // 若是是数组
          if ( copyIsArray ) {
            // 将copyIsArray从新设置为false,为下次遍历作准备。
            copyIsArray = false;
            // 判断被扩展的对象中src是否是数组
            clone = src && jQuery.isArray(src) ? src : [];
          } else { 
            // 判断被扩展的对象中src是否是纯对象
            clone = src && jQuery.isPlainObject(src) ? src : {};
          }递归

          // 递归调用extend方法,继续进行深度遍历
          target[ name ] = jQuery.extend( deep, clone, copy );

        // 若是不须要深度复制,则直接把copy(第i个被扩展对象中被遍历的那个键的值)
        } else if ( copy !== undefined ) {
          target[ name ] = copy;
        }
      }
    }
  }

  // 原对象被改变,所以若是不想改变原对象,target可传入{}
  return target;
};

 
分类:  js
相关文章
相关标签/搜索