这篇主要说一下在源码中jquery对象是怎样设计实现的,下面是相关代码的简化版本:

 (function( window, undefined ) {
// code 定义变量
jQuery = function( selector, context ) {
return new jQuery.fn.init( selector, context, rootjQuery );
},
// code 定义变量
jQuery.fn = jQuery.prototype = {
jquery: core_version,
constructor: jQuery,
init: function( selector, context, rootjQuery ) {
// code 初始化、参数处理
}
// code 一些方法(each、ready、first、eq等)
}
jQuery.fn.init.prototype = jQuery.fn;
// code 其他
if ( typeof window === "object" && typeof window.document === "object" ) {
window.jQuery = window.$ = jQuery;
}
})( window );

首先,回顾一下javascript中相关知识。

在javascript中特定类型的对象是通过构造函数来创建的,例如:

 function Person(name){
this.name = name;
this.sayName = function(){
alert(this.name);
}
}
// 作为普通函数使用
Person('Yanger90');
window.sayName(); // 作为构造函数使用
var person = new Person('Yanger90');
person.sayName();

更好的方式-原型模式

function Person(){}
Person.prototype = {
name: "Yanger90",
syaName: function(){
console.log(this.name);
}
};
var person = new Person();

每一个函数都有一个prototype(原型)属性,里面包含的属性和方法,是所有通过该构造函数创建的实例对象所共享的。对于一些公用的方法,像例子中的sayName方法,就可以放在原型中共享而不用像第一种方式那样,每个实例对象都要重新创建一遍。

好了,基础知识就简单介绍到这,详细可参阅《javascript高级程序设计》这本书。

回到jquery中,我们一般使用jquery语法类似这样:

$(element).css();

选择元素然后执行相应方法,那么前面的$(element)就应该是一个实例对象,再调用其方法。

我们看到在源码开始的部分就定义了jQuery变量:

jQuery = function( selector, context ) {
return new jQuery.fn.init( selector, context, rootjQuery );
}

它确实返回了一个实例对象,构造函数是init,接着往下看。

jQuery.fn = jQuery.prototype = {
jquery: core_version,
constructor: jQuery, // 修正以字面量方式重写原型对象造成的指向问题
init: function( selector, context, rootjQuery ) {
// code 初始化、参数处理
}
// code 一些方法(each、ready、first、eq等)
}

找到init发现它是jQuery原型(prototype)中的一个方法。

问题来了,init方法中只是对参数进行了处理,并没有我们常用的each、ready、first、eq等方法,它们都在jQuery原型(prototype)中,所以还无法调用这些方法,那么继续往后看。

jQuery.fn.init.prototype = jQuery.fn;

这句话把init的原型指向了jQuery.fn,也就是jQuery.prototype,这样一来,jQuery原型(prototype)中的属性和方法就共享给了通过init构造函数创建的实例对象,也就实现了继承。

最后,在jquery源码的末尾有一句

window.jQuery = window.$ = jQuery;

jQuery是在匿名函数中定义的,所以外部是无法访问的,这里将它赋值给window对象的属性,这样我们就可以在外部直接使用了。

Jquery源码中的Javascript基础知识(三)的更多相关文章

  1. Jquery源码中的Javascript基础知识(一)

    jquery源码中涉及了大量原生js中的知识和概念,文章是我在学习两者的过程中进行的整理和总结,有不对的地方欢迎大家指正. 本文使用的jq版本为2.0.3,附上压缩和未压缩版本地址: http://a ...

  2. Jquery源码中的Javascript基础知识(二)

    接上一篇,jquery源码的这种写法叫做匿名函数自执行 (function( window, undefined ) { // code })( window ); 函数定义了两个参数window和u ...

  3. Jquery源码中的Javascript基础知识(四)— jQuery.fn.init方法

    $() 即调用了jQuery.fn.init方法 jQuery = function( selector, context ) { return new jQuery.fn.init( selecto ...

  4. jquery源码中noConflict(防止$和jQuery的命名冲突)的实现原理

    jquery源码中noConflict(防止$和jQuery的命名冲突)的实现原理 最近在看jquery源码分析的视频教学,希望将视频中学到的知识用博客记录下来,更希望对有同样对jquery源码有困惑 ...

  5. jQuery源码中的“new jQuery.fn.init()”什么意思?

    所有文章搬运自我的个人主页:sheilasun.me 引子 最近打算试试看看jQuery的源码,刚开个头就卡住了.无论如何都理解不了jQuery源码入口部分中的 return new jQuery.f ...

  6. jQuery源码中的赌博网站

    前言 jQuery源码中有赌博网站? 起因是公司发的一份自查文件,某银行在日常安全运营过程中发现在部分jQuery源码中存在赌博和黄色网站链接. 链接分为好几个: www.cactussoft.cn ...

  7. 关于jQuery源码中(function(window,undefined){//dosomething()})(window)写法解释

    一.首先是最常见的闭包 (Closure) 范式自执行函数的写法,这里用匿名函数封装(构造块级作用域),避免了匿名函数内部的代码与外部之间发生冲突(如使用了相同的变量名). (function() { ...

  8. jQuery 源码中的 camelCase

    先看一下源码 //65-72行 // Matches dashed string for camelizing //匹配连字符 ‘-’ 和其后的第一个字母或数字,如果是字母,则替换为大写,如果是数字, ...

  9. 如何从源码中学习javascript

    艾伦说啊,学习javascript,必须要学会看源码,通过高手的源码,你可以从中吸取很多书本上难以看到的技巧. 看源码就好像喝鸡汤,所有的营养都在这汤里了.这汤就是源码,高手写的源码,就是最好的鸡汤. ...

随机推荐

  1. c#实现Socket网络编程

    命名空间: 在网络环境下,我们最感兴趣的两个命名空间是System.Net和 System.Net.Sockets. System.Net命名空间通常与较高程的操作有关,例如download或uplo ...

  2. Openstack os-networks API create network 方法

    官方文档在请求方法和地址上有错误: http://api.openstack.org/api-ref.html#ext-os-networks 正确的地址为: /v2/{tenant_id}/os-n ...

  3. 斌哥的 Docker 进阶指南—监控方案的实现

    过去的一年中,关于 Docker 的话题从未断过,而如今,从尝试 Docker 到最终决定使用 Docker 的转化率依然在逐步升高,关于 Docker 的讨论更是有增无减.另一方面,大家的注意力也渐 ...

  4. root 授权

    错误:The user specified as a definer ('root'@'%') does not exist 解决: grant all privileges on *.* to ro ...

  5. BZOJ 2424: [HAOI2010]订货 费用流

    2424: [HAOI2010]订货 Description 某公司估计市场在第i个月对某产品的需求量为Ui,已知在第i月该产品的订货单价为di,上个月月底未销完的单位产品要付存贮费用m,假定第一月月 ...

  6. js判断一个对象是否包含属性的方式

    判断一个对象是不是包含属性,我们这里提供三种方式 1,使用in 运算符 var obj = {name:'liwei'}; alert('name' in obj); // return true a ...

  7. lintcode:背包问题

    背包问题 在n个物品中挑选若干物品装入背包,最多能装多满?假设背包的大小为m,每个物品的大小为A[i] 样例 如果有4个物品[2, 3, 5, 7] 如果背包的大小为,可以选择的空间. 如果背包的大小 ...

  8. 2011 ACM-ICPC 成都赛区解题报告(转)

    2011 ACM-ICPC 成都赛区解题报告 首先对F题出了陈题表示万分抱歉,我们都没注意到在2009哈尔滨赛区曾出过一模一样的题.其他的话,这套题还是非常不错的,除C之外的9道题都有队伍AC,最终冠 ...

  9. 如何用crontab运行一个图形化界面的程序

    crontab是linux中定时任务的 执行crontab -e可以编辑定时列表(export DISPLAY=:0 指定显示器或者export DISPLAY=localhost:0) 15 13 ...

  10. Visual studio C#语言输出调试信息到Output窗口方法

    1.菜单栏: 工具>选项>调试>将所有输出窗口文本重定向到即时窗口          2.使用Console.WriteLine或Write添加调试信息 3.按F5启动调试程序 4. ...