jQuery筆記: 基本概念與jQuery核心

@
jquery

轉載請註明出處數組

初識jQuery

爲何要使用jQuery?

1.什麼是jquery?
jQuery是js的一個庫,簡化了js代碼的書寫(注:jQuery語句中用逗號分隔各個css,由於一條css對應一個對象屬性,對象屬性之間是用逗號分隔而非分號)
舉例:
例1:簡化了獲取元素的語句 + 設置樣式的書寫變得更加直觀好記
例2:jQuery解決了兼容性問題promise

注:由於jQuery是js的一個庫,引入的時候就是一個js文件,因此,咱們是能夠用原生js代碼來修改jQuery文件的?網絡


如何使用jQuery?

1.下載jQuery庫
壓縮版本compressed:體積小,方便網絡傳輸;但不易於閱讀。多用於實際使用。
未壓縮版本uncompressed: 體積大,便於閱讀,多用於開發。
2.引入jQuery庫
本地引入:同js同樣,用script引入,服從目錄語法
網絡引入:示例閉包

<script src="//code.jquery.com/jquery-1.11.0.min.js"></script>

jQuery與js加載模式不一樣

1.入口函數的加載模式不一樣:app

  • 原生js的window.onload會等到頁面元素及連接的資源都加載完畢纔會執行
  • jQuery的ready()等到頁面元素加載完畢就執行,不會等待其餘資源加載

2.重複爲同一元素添加事件的不一樣框架

  • 原生JS爲同一元素添加多個事件,後添加的覆蓋先添加的
  • jQuery爲同一元素添加多個事件,後者不會覆蓋前者

jQuery入口函數的四種寫法

1.\$ (document).ready(function(){......});
2.\$ (function(){......});
3.第一種中的\$ 換成jQuery
4.第二種裏的\$ 換成jQuery
咱們遵循write less,do more的原則,推薦使用第二種寫法。less


jQuery的訪問符衝突問題

1.jQuery訪問符衝突問題: jQuery框架與其餘框架都使用了\$ 時,書寫代碼時,使用\$ 就會有衝突(後引進的框架覆蓋先引進的)。
2.解決辦法:函數

  • 釋放訪問符\$ 的使用權,改成jQuery。例:
    jQuery.noConflict();
    jQuery(function(){......});
    釋放\$ 使用權以後,就不能用\$ 編寫jQuery代碼了,會無效。
    釋放操做必須在用jQuery編寫代碼以前。

  • 自定義新的訪問符。例:
    var Q = jQuery.noConflict();
    Q(function(){......});

jQuery核心函數和jQuery對象實質

1.jQuery核心方法是什麼?
jQuery的核心方法就是jQuery(),或者說\$ ().

2.jQuery核心方法接收的參數有哪些狀況?

  • 回調函數:\$ (callback());
    執行回調函數,並返回一個jQuery對象
  • 字符串選擇器:\$ ('.center');
    返回一個jQuery對象,保存了找到的DOM元素
  • 字符串代碼片斷:\$ ('< p >我是P< /p >');
    按照代碼片斷建立元素,並返回一個包含該元素的jQuery對象(注意:該元素並未添加至文檔樹,須要用額外代碼來添加)
  • DOM元素: \$ (document.getElementById('box'));
    返回一個jQuery對象,保存了該DOM元素

3.jQuery對象詳解

  • jQuery方法框架結構分析:
    框架:

    仔細看咱們就能夠發現,這個框架只不過是兩個當即執行函數的嵌套:
    外層的:(function (window,undefined){})(window)
    內層的:var jQuery = (function (){})())
    而在內層的IIFE中:

    • 先定義了內層函數(閉包)jQuery
    • 接着令閉包jQuery的屬性fn與原型prototype都指向一個新建的字面量對象,該字面量對象中定義了屬性constructor,length等;也定義了許多函數,其中就包含了最核心的init函數.
    • 而後,將init函數的原型prototype指向init所在的字面量對象.
    • 最後將閉包jQuery返回給外層IIFE.
      下圖爲內層IIFE中定義的閉包jQuery的重要引用的分佈:

在後面的分析咱們會知道--jQuery對象的實質就是jQuery.fn.init的實例,所以結合上圖,咱們不難發現:
1.自定義的字面量對象就是init的原型對象
2.咱們經過jQuery.fn.init.prototype或者jQuery.prototype都可訪問和修改init的原型

分析完內層,咱們接着分析框架中的外層IIFE:
(1) 將內層IIFE的返回值(內層的jQuery函數)賦給外層變量jQuery
(2) 定義全局變量jQuery,\$ ,並將上一步jQuery的值賦給它們(jQuery()與\$ ()的效果相同的緣由)

  • jQuery對象的實質
    jQuery對象就是jQuery方法的返回值,由上面的分析:
    由代碼return new jQuery.fn.init(selector, context, rootjQuery);可知,jQuery方法的返回值,即jQuery對象就是jQuery.fn.init的實例.

3.jQuery對象是一個僞數組對象
僞數組對象:

  • 含有屬性length
  • 另外含有length個屬性,這些屬性鍵名爲0到length-1

4.使用jQuery與使用原生js有什麼區別麼?在jQuery中是否能使用原生js代碼呢?

  • 首先,從概念上,咱們知道jQuery是js的一個庫,咱們下載和引入的jQuery文件後綴都是".js".所以,概念上來講,jQuery本質就是js.
  • 其次,jQuery從定義框架來看,他就是jQuery構造函數 + 自定義原型對象 + 自定義原型對象.init 這三個主要部分構成.
  • 其三,jQuery方法的定義中,閉包jQuery的原型從Function(){}改成了自定義對象,那麼其原型鏈上就再也不包含call函數.所以,不能經過其餘對象調用jQuery的構造函數.也就是說:jQuery.call(obj,...)是錯誤的.
    [jQuery對象原型鏈以下]:jQuery.fn.init實例-->jQuery.fn/jQuery.prototype-->Object.prototype

jQuery重要方法--參考資料

1.靜態jQuery.ready方法與實例.ready()方法

  • jQuery的兩個插件擴展方法
    • jQuery.extend(object):擴展jQuery構造函數自己,添所謂'靜態方法'(直接用構造函數名調用)
    • jQuery.fn.extend(object):擴展jQuery原型對象,添加所謂'實例方法'(按習慣,用實例對象調用)
    • 這兩個方法實際上是同一個函數,只是this的值不一樣,致使了效果的不一樣.
      這兩個方法定義時,是這麼一種形式:
      jQuery.extend = jQuery.fn.extend = function() {
      //實現代碼
      }
  • 兩個ready方法
    • '靜態'jQuery.ready的定義:
      源碼中的定義形式:

      jQuery.extend({
      ready:function (){}
      });

      說明:
      (1).此方法返回一個類promise對象,當DOM加載就緒時,該對象變得能夠解析.(即:當DOM加載就緒時,能夠用該對象訪問其屬性,調用其方法等等)
      (2).該方法的返回值會被jQuery.when,Promise.resolve()以及 .ready()方法中使用

    • 實例方法--.ready()
      源碼定義以下:

      jQuery.fn.ready = function( fn ) {
      jQuery.ready.promise().done( fn );//當DOM加載就緒時,調用promise()方法並執行fn函數
      return this;
      };

      說明: .ready(fn) 函數--當DOM加載就緒時執行fn函數

    • jQuery.holdReady(hold)方法
      說明:經過hold(取值:true/false)來延遲/取消延遲jQuery的ready事件.

2.'靜態'類型檢測方法

  • jQuery.isFunction(obj)
  • jQuery.isArray(obj)
  • jQuery.isWindow(obj)
  • jQuery.isNumeric(obj)
  • jQuery.isEmptyObject(obj)
  • jQuery.isPlainObject(obj)

3.'靜態'jQuery.each(obj,fn)方法
源碼定義: 靜態jQuery.each是用jQuery.extend()定義在jQuery對象自己上的
(對應的實例.each方法定義在原型上,實質是將靜態jQuery.each方法的this換了一下)

each: function( obj, callback ) {
var length, i = 0;
if ( isArrayLike( obj ) ) { //針對類數組
length = obj.length;
for ( ; i < length; i++ ) {
if ( callback.call( obj[ i ], i, obj[ i ] ) === false ) {
break; //當回調函數返回false時,跳出整個循環
}
}
} else {
for ( i in obj ) { //針對enumerable不爲false的通常對象
if ( callback.call( obj[ i ], i, obj[ i ] ) === false ) {
break; //當回調函數返回false時,跳出整個循環
}
}
}
return obj;
}

源碼分析:

(1) 針對類數組對象,對每個數字鍵值i,執行obj[i].callback(i,obj[i]).若是遇到某一項返回值爲false,跳出循環,終止遍歷

(2) 針對通常對象,使用in操做符,對於每個可遍歷鍵值i,執行obj[i].callback(i,obj[i]).若是遇到某一項返回值爲false,跳出循環,終止遍歷
總結:

(1) 類數組不遍歷非數字鍵值屬性

(2) 通常對象不遍歷enumerable爲false的屬性

(3) 一旦遍歷過程當中某一次函數調用返回值爲false,終止遍歷

(4) 整個.each的返回值爲被遍歷的對象

4.'靜態' jQuery.map(elems,callback,arg)方法
源碼定義:

// arg is for internal usage only
map: function( elems, callback, arg ) {
    var length, value,
        i = 0,
        ret = [];

    // Go through the array, translating each of the items to their new values
    if ( isArrayLike( elems ) ) {  //針對類數組
        length = elems.length;
        for ( ; i < length; i++ ) {
            value = callback( elems[ i ], i, arg );

            if ( value != null ) {
                ret.push( value ); 
            }  //將value中的值添加到數組末尾,並返回新的數組的長度
        }

    // Go through every key on the object,
    } else {
        for ( i in elems ) {  //針對enumerable非false的通常對象
            value = callback( elems[ i ], i, arg );

            if ( value != null ) {
                ret.push( value );
            } //將value中的值添加到數組末尾,並返回新的數組長度
        }
    }

    // Flatten any nested arrays
    return concat.apply( [], ret ); 
}  //Array.prototype.concat(合併數組,返回新數組) + Object.prototype.apply

源碼分析:

(1) 針對類數組對象,對每個數字鍵值 i ,調用callback( elems[ i ], i, arg ),並將其中非null的返回值添加到數組ret中

(2) 針對通常對象,對每個屬性名 i ,調用callback( elems[ i ], i, arg ),並將其中非null的返回值添加到數組ret中
總結:

(1) 類數組不遍歷非數字鍵值屬性

(2) 通常對象不遍歷enumerable爲false的屬性

(3) 遍歷過程當中,某一次函數調用返回值爲null時,結果不計入ret中(咱們能夠靈活控制callback方法的返回值來達到咱們想要的效果)

(4) 整個jQuery.map的返回值爲被遍歷的對象被處理後所獲得的數組ret

相關文章
相關標籤/搜索