jQuery extend()详解及简单实例


Posted in jQuery onMay 06, 2017

jQuery extend()详解及简单实例

使用jQuery的时候会发现,jQuery中有的函数是这样使用的:

$.get(); 
$.post(); 
$.getJSON();

有些函数是这样使用的:

$('div').css(); 
$('ul').find('li');

有些函数是这样使用的:

$('li').each(callback); 
$.each(lis,callback);

这里涉及到两个概念:工具方法与实例方法。通常我们说的工具方法是指无需实例化就可以调用的函数,如第一段代码;实例方法是必须实例化对象以后才可以调用的函数,如第二段代码。jQuery中很多方法既是实例方法也是工具方法,只是调用方式略有不同,如第三段代码。为了更清晰解释JavaScript中的工具方法与实例方法,进行如下测试。

functionA(){ 
     
  } 
  A.prototype.fun_p=function(){console.log("prototpye");}; 
  A.fun_c=function(){console.log("constructor");}; 
  var a=new A(); 
  A.fun_p();//A.fun_p is not a function 
  A.fun_c();//constructor 
  a.fun_p();//prototpye 
  a.fun_c();//a.fun_c is not a function

通过以上测试可以得出结论,在原型中定义的是实例方法,在构造函数中直接添加的是工具方法;实例方法不能由构造函数调用,同理,工具方法也不能由实例调用。

当然实例方法不仅可以在原型中定义,有以下三种定义方法:

functionA(){ 
    this.fun_f=function(){ 
        console.log("Iam in the constructor"); 
    }; 
} 
A.prototype.fun_p=function(){ 
    console.log("Iam in the prototype"); 
}; 
var a=newA(); 
a.fun_f();//Iam in the constructor 
a.fun_i=function(){ 
    console.log("Iam in the instance"); 
}; 
a.fun_i();//Iam in the instance 
a.fun_p();//Iam in the prototype

这三种方式的优先级为:直接定义在实例上的变量的优先级要高于定义在“this”上的,而定义在“this”上的又高于 prototype定义的变量。即直接定义在实例上的变量会覆盖定义在“this”上和prototype定义的变量,定义在“this”上的会覆盖prototype定义的变量。

下面看jQuery中extend()方法源码:

jQuery.extend = jQuery.fn.extend = function() { 
    var options,name, src, copy, copyIsArray, clone, 
        target= arguments[0] || {}, 
        i =1, 
        length= arguments.length, 
        deep= false; 
    // Handle adeep copy situation 
    if ( typeoftarget === "boolean" ) { 
        deep= target; 
        //Skip the boolean and the target 
        target= arguments[ i ] || {}; 
        i++; 
    } 
    // Handlecase when target is a string or something (possible in deep copy) 
    if ( typeoftarget !== "object" && !jQuery.isFunction(target) ) { 
        target= {}; 
    } 
    // ExtendjQuery itself if only one argument is passed 
    if ( i ===length ) { 
        target= this; 
        i--; 
    } 
    for ( ; i< length; i++ ) { 
        //Only deal with non-null/undefined values 
        if ((options = arguments[ i ]) != null ) { 
            //Extend the base object 
            for( name in options ) { 
                src= target[ name ]; 
                copy= options[ name ]; 
                //Prevent never-ending loop 
                if( target === copy ) { 
                   continue; 
                } 
                //Recurse if we're merging plain objects or arrays 
                if( deep && copy && ( jQuery.isPlainObject(copy) || (copyIsArray= jQuery.isArray(copy)) ) ) { 
                   if( copyIsArray ) { 
                       copyIsArray= false; 
                       clone= src && jQuery.isArray(src) ? src : []; 
                   }else { 
                       clone= src && jQuery.isPlainObject(src) ? src : {}; 
                   } 
                   //Never move original objects, clone them 
                   target[name ] = jQuery.extend( deep, clone, copy ); 
                //Don't bring in undefined values 
                }else if ( copy !== undefined ) { 
                   target[name ] = copy; 
                } 
            } 
        } 
    } 
    // Returnthe modified object 
    return target; 
};

(1)首先,jQuery和其原型中extend()方法的实现使用的同一个函数。

(2)当extend()中只有一个参数的时候,是为jQuery对象添加插件。在jQuery上扩展的叫做工具方法,在jQuery.fn(jQuery原型)中扩展的是实例方法,即使在jQuery和原型上扩展相同名字的函数也可以,使用jQuery对象会调用工具方法,使用jQuery()会调用实例方法。

(3)当extend()中有多个参数时,后面的参数都扩展到第一个参数上。

var a={}; 
$.extend(a,{name:"hello"},{age:10}); 
console.log(a);//Object{name: "hello", age: 10}

(4)浅拷贝(默认):   

var a={}; 
varb={name:"hello"}; 
$.extend(a,b); 
console.log(a);//Object{name: "hello"} 
a.name="hi"; 
console.log(b);//Object{name: "hello"}

b不受a影响,但是如果b中一个属性为对象:

var a={}; 
varb={name:{age:10}}; 
$.extend(a,b); 
console.log(a.name);//Object{age: 10} 
a.name.age=20; 
console.log(b.name);//Object{age: 20}

由于浅拷贝无法完成,则b.name会受到a的影响,这时我们往往希望深拷贝。

深拷贝:   

var a={}; 
varb={name:{age:10}}; 
$.extend(true,a,b); 
console.log(a.name);//Object{age: 10} 
a.name.age=20; 
console.log(b.name);//Object{age: 10}

b.name不受a的影响。

var a={name:{job:"Web Develop"}}; 
var b={name:{age:10}}; 
$.extend(true,a,b); 
console.log(a.name);//age: 10 job: "Web Develop"
//b.name没有覆盖a.name.job。

感谢阅读,希望能帮助到大家,谢谢大家对本站的支持!

jQuery 相关文章推荐
jQuery输入框密码的显示隐藏【代码分享】
Apr 29 jQuery
jQuery遮罩层实例讲解
May 11 jQuery
jQuery插件imgAreaSelect基础讲解
May 26 jQuery
jquery网页加载进度条的实现
Jun 01 jQuery
jQuery实现QQ空间汉字转拼音功能示例
Jul 10 jQuery
jquery.validate.js 多个相同name的处理方式
Jul 10 jQuery
jQuery简单实现对数组去重及排序操作实例
Oct 31 jQuery
jQuery实现鼠标点击处心形漂浮的炫酷效果示例
Apr 12 jQuery
深入浅析angular和vue还有jquery的区别
Aug 13 jQuery
JQuery实现ajax请求的示例和注意事项
Dec 10 jQuery
jQuery实现的简单日历组件定义与用法示例
Dec 24 jQuery
jQuery 选择器用法实例分析【prev + next】
May 22 jQuery
jquery仿微信聊天界面
May 06 #jQuery
简单实现jQuery弹幕效果
May 06 #jQuery
jquery实现提示语淡入效果
May 05 #jQuery
Jquery获取radio选中的值
May 05 #jQuery
jQuery实现简单的抽奖游戏
May 05 #jQuery
jquery中each循环的简单回滚操作
May 05 #jQuery
jquery dataTable 获取某行数据
May 05 #jQuery
You might like
php adodb分页实现代码
2009/03/19 PHP
thinkphp的CURD和查询方式介绍
2013/12/19 PHP
php中\r \r\n \t的区别示例介绍
2014/02/08 PHP
PHP获取photoshop写入图片文字信息的方法
2015/03/31 PHP
网页javascript精华代码集
2007/01/24 Javascript
js有序数组的连接问题
2013/10/01 Javascript
appendChild() 或 insertBefore()使用与区别介绍
2013/10/11 Javascript
jQuery formValidator表单验证
2016/01/07 Javascript
使用jQuery Ajax 请求webservice来实现更简练的Ajax
2016/08/04 Javascript
原生js实现手风琴功能(支持横纵向调用)
2017/01/13 Javascript
RequireJS 依赖关系的实例(推荐)
2017/01/21 Javascript
微信小程序中的swiper组件详解
2017/04/14 Javascript
Angularjs使用过滤器完成排序功能
2017/09/20 Javascript
JS与jQuery实现ListBox上移,下移,左移,右移操作功能示例
2018/05/31 jQuery
VUE实现可随意拖动的弹窗组件
2018/09/25 Javascript
详解webpack打包时排除其中一个css、js文件或单独打包一个css、js文件(两种方法)
2018/10/26 Javascript
利用Webpack实现小程序多项目管理的方法
2019/02/25 Javascript
javascript实现超好看的3D烟花特效
2020/01/01 Javascript
vue 虚拟DOM的原理
2020/10/03 Javascript
微信小程序实现modal弹出框遮罩层组件(可带文本框)
2020/12/20 Javascript
Python 元组(Tuple)操作详解
2014/03/11 Python
Python自动化运维_文件内容差异对比分析
2017/12/13 Python
python实现决策树分类算法
2017/12/21 Python
django1.11.1 models 数据库同步方法
2018/05/30 Python
PyQt5实现QLineEdit添加clicked信号的方法
2019/06/25 Python
Pandas_cum累积计算和rolling滚动计算的用法详解
2019/07/04 Python
python安装mysql的依赖包mysql-python操作
2021/01/01 Python
亚马逊印度站:Amazon.in
2017/10/15 全球购物
护理专业应届毕业生推荐信
2013/11/15 职场文书
《狼》教学反思
2014/03/02 职场文书
2014年道德讲堂实施方案
2014/03/05 职场文书
平安工地建设方案
2014/05/06 职场文书
我爱我校演讲稿
2014/05/21 职场文书
爱护公物演讲稿
2014/09/09 职场文书
python numpy中setdiff1d的用法说明
2021/04/22 Python
5个pandas调用函数的方法让数据处理更加灵活自如
2022/04/24 Python