欢迎您访问程序员文章站本站旨在为大家提供分享程序员计算机编程知识!
您现在的位置是: 首页

jquery 源码解读

程序员文章站 2022-07-13 12:34:49
...

jquery 源码大概10000多行,每行都会解析可能不是很现实,可能也只会更新一版,这都看心情。

function(global,factory){...})()

在这部分主要就是匿名函数
注释:匿名函数的好处:自执行里面所有东西都是局部的,防止和代码冲突
那如何获取匿名函数里面的方法和属性呢?
可以在里面挂在一个对象上,比如挂在windows上面

(function (){
    function abc (){}
    window.abc = abc
})()
    abc()   

"use strict"

js的严禁模式;
在js严格模式,对js做了一些限制,主要有以下作用:
1.消除js语法不合理,不严谨的,减少怪异行为
2.消除代码运行的一些不安全之处
3.提高编译效率,加强运行速度。
4.对未来新版本做好铺垫。
语法的改变:
1.全局命名必须是 v=1 其他变量var
2.禁止使用with 创设 eval作用域。
3.禁止this 指向全局window
4.禁止内部函数遍历调用栈
function f1(){
f1.caller 报错
f1.arguments 报错
}
5.禁止删除变量,只有在configurable 设置为true
6.使用get方法赋值会报错。
var o = {
get v(){return 1;}
}
o.v() =2 //报错
7.删除一个不可删除的属性, delete Object.prototype.
8.重命名错误
9.参数名重复错误。
10.禁止八进制
11.对arguments 参数做了限制。比如不能复制,不能追踪参数变化,不能用callee。
12.函数声明在顶层,不许在非函数代码内声明函数
13.保留字


( typeof window !== "undefined" ? window : this, function( window, noGlobal )

这句话很清楚 判断window 返回类型。
typeof 可以判断 object undefined null boolean number string Symbol functuon在ECMA-262条款中实现了


var arr = [];

var document = window.document;

var getProto = Object.getPrototypeOf;

var slice = arr.slice;

var concat = arr.concat;

var push = arr.push;

var indexOf = arr.indexOf;

var class2type = {};

var toString = class2type.toString;

var hasOwn = class2type.hasOwnProperty;

var fnToString = hasOwn.toString;

var ObjectFunctionString = fnToString.call( Object );

var support = {};       

上面声明了一些方法和一些变量。
slice 这个方法,数组中返回选定得元素。 用法arr.slice(start,end) start -1 最后一个元素。 这个方法会返回一个新数组。


var isFunction = function isFunction( obj ) {

      // Support: Chrome <=57, Firefox <=52
      // In some browsers, typeof returns "function" for HTML <object> elements
      // (i.e., `typeof document.createElement( "object" ) === "function"`).
      // We don't want to classify *any* DOM node as a function.
      return typeof obj === "function" && typeof obj.nodeType !== "number";
  };


var isWindow = function isWindow( obj ) {
        return obj != null && obj === obj.window;
    };




    var preservedScriptAttributes = {
        type: true,
        src: true,
        noModule: true
    };

    function DOMEval( code, doc, node ) {
        doc = doc || document;

        var i,
            script = doc.createElement( "script" );

        script.text = code;
        if ( node ) {
            for ( i in preservedScriptAttributes ) {
                if ( node[ i ] ) {
                    script[ i ] = node[ i ];
                }
            }
        }
        doc.head.appendChild( script ).parentNode.removeChild( script );
    }


function toType( obj ) {
    if ( obj == null ) {
        return obj + "";
    }

    // Support: Android <=2.3 only (functionish RegExp)
    return typeof obj === "object" || typeof obj === "function" ?
        class2type[ toString.call( obj ) ] || "object" :
        typeof obj;
}
/* global Symbol */
// Defining this global in .eslintrc.json would create a danger of using the global
// unguarded in another place, it seems safer to define global only for this module

一些代码,工具类吧 …


version = "3.3.1", 版本号
jQuery = function( selector, context ) {
    return new jQuery.fn.init( selector, context );
}, 
翻译是构造函数的增强。可能是用来报错的吧。

jQuery.fn = jQuery.prototype = {
    jquery: version,
    constructor: jQuery,
    length: 0, //在这里看了下这个对象的长度.
    toArray: function() {
        return slice.call( this );
    }, 居然是操作DOM的方法.尴尬...
    get: function( num ) {
        if ( num == null ) {
            return slice.call( this );
        }
        return num < 0 ? this[ num + this.length ] : this[ num ];
    },
    pushStack: function( elems ) {

        // Build a new jQuery matched element set
        var ret = jQuery.merge( this.constructor(), elems );

        // Add the old object onto the stack (as a reference)
        ret.prevObject = this;

        // Return the newly-formed element set
        return ret;
    },

    // Execute a callback for every element in the matched set.
    each: function( callback ) {
        return jQuery.each( this, callback );
    },

    map: function( callback ) {
        return this.pushStack( jQuery.map( this, function( elem, i ) {
            return callback.call( elem, i, elem );
        } ) );
    },

    slice: function() {
        return this.pushStack( slice.apply( this, arguments ) );
    },

    first: function() {
        return this.eq( 0 );
    },

    last: function() {
        return this.eq( -1 );
    },

    eq: function( i ) {
        var len = this.length,
            j = +i + ( i < 0 ? len : 0 );
        return this.pushStack( j >= 0 && j < len ? [ this[ j ] ] : [] );
    },

    end: function() {
        return this.prevObject || this.constructor();
    },

    // For internal use only.
    // Behaves like an Array's method, not like a jQuery method.
    push: push,
    sort: arr.sort,
    splice: arr.splice
};

上面的方法都是DOM操作的。很幽默哦~ 当然当年jquery最主要的核心就是选择器,那么当年最辉煌的就是dom操作吧。


jQuery.extend = jQuery.fn.extend = function() {

代码补充,如果之前写了 那么将会被覆盖~