jQuery源码分析随笔

一次在写jquery插件的经历,让自己发现了js水很深,自己很菜。然后慢慢发现js包括了原型、闭包、作用域等一些很常用的知识点。

 

首先jquery源码的主要结构

下面就是在做分析jquery源码时自己的一些备注

 1 (function(window){
 2     var jQuery = function(select){
 3         //privatefunc();
 4         return new jQuery.fn.init(select);
 5         //这边必须new一个对象(这时this指向init对象),不然return jQuery.fn.init(select);中this指向jQuery.fn,而jQuery.fn其实是个定义了很多方法的集合
 6     }
 7     
 8     jQuery.test = function(){//静态方法
 9         console.log('call test method');
10     }
11     
12     var privatefunc = function (){//内部方法,不能再 外面调用,需要让外部调用及jquery的做法:window.privatefunc = privatefunc;这也是闭包
13         console.log(this)
14         console.log('call privatefunc method');
15     }
16 
17     jQuery.fn = jQuery.prototype = {
18         init:function(select){
19             console.log(this)
20             var _this = this;
21             if(!select){
22                 return this;
23             }
24             _this.ele = document.documentElement.querySelectorAll(select);
25             _this.length = _this.ele.length;
26             return _this;
27         },
28         show: function(){
29             if(this.length===0){
30                 return;
31             }
32             for(var i=0;i<this.length;i++){
33                 this.ele[i].style.display = 'block';
34             }
35             console.log('call show method')
36             return this;
37         },
38         hide: function(){
39             if(this.length===0){
40                 return;
41             }
42             for(var i=0;i<this.length;i++){
43                 this.ele[i].style.display = 'none';
44             }
45             console.log('call hide method')
46             return this;
47         },
48         click: function(){
49             console.log('call click method')
50             return this;
51         },
52         each: function(fn){
53             for(var i=0;i<this.length;i++){
54                 fn.call(this.ele[i], i, this.ele[i])
55             }
56         },
57         morefunc: function(){
58             
59         }
60         
61     }
62     
63     jQuery.fn.init.prototype = jQuery.fn;
64     
65     window.jQuery = jQuery; //将jQuery赋值给window.jQuery,全局变量。这样外部就可以直接访问jQuery函数了
66     
67 })(window,undefined)

下面我从自己一开始比较疑惑的几个点进行分析

1、jQuery 到底是什么?

  通常$('div')返回的是new jQuery.fn.init( selector, context )这个对象,也就是init这个函数对象,这里面会查询div标签的dom对象数组、length还有jquery的实例方法。

  

 

2、jQuery.fn和jQuery的区别?

  jQuery.fn是个方法的集合,通过jQuery.fn.init.prototype = jQuery.fn,这样jQuery.fn.init就包含了jQuery的所有实例方法,jQuery.fn也就是jQuery的所有实例方法。

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

 

3、jQuery为什么要调用jQuery.fn.init来实例化?

  jQuery的初始化可以$('div')、new $('div')。为了能通过$('div')方便的进行初始化,就需要在构造方法中返回new jQuery.fn.init(select)来巧妙的实现他。

  jQuery.fn.init刚好具备了jquery的所有的实例方法。

  比如在jQuery构造方法中直接return this或者new jQuery(),很明显这是没办法实现的。

 

4、存在的疑问

   jQuery.fn这个变量总是让人很绕。如果直接换成jQueryFn不知道可不可以,也许是为了写插件时把jQuery.prototype提供出去吧。

  jQuery.fn.plugin = plugin;

 

5、总结

  首先创建一个闭包,在里面申请一个变量jQuery,然后挂载window下,让闭包外的作用域也能进行访问;

  其次创建一个jquery别名的jquery.fn=jquery.prototype,并将jquery.fn.init.prototype = jquery.fn;
     最后$('.div')的方法返回new jquery.fn.init()的实例。这样这个实例也拥有了jquery.fn的方法。

1 (function(window, undefined){
2 var jquery = function(selected, content){
3 return jquery.fn.init();
4 }
5 //方便后续我们初始化jquery对象时$('div')而不用new jQuery('div')来初始化
6 jquery.fn.init.prototype = jquery.fn;
7 
8 })(window)

 

posted @ 2017-03-07 20:34  这月过后  阅读(272)  评论(0编辑  收藏  举报