1. 程式人生 > >js高級程序設計 筆記 --- 面向對象的程序設計

js高級程序設計 筆記 --- 面向對象的程序設計

delet 執行 面向 getter for-in循環 desc 函數綁定 模式 函數傳遞

1,理解對象

  通過對象字面量的方式,創建一個對象,為它添加屬性和方法:

    var obj = { a: 1, b:2, sayA(){ console.log(this.a)}}

  1,屬性類型:

    數據屬性 :

      數據屬性包含一個數據值的位置。在這個位置可以讀取和寫入值。有四個特性

      configurable enumerable writable value : 分為的意思為:是否能通過delete刪除(能否修改特性)、是否能通過for-in循環、是否能修改屬性的值、包含這個屬性的值

      通過對象字面量創建的對象,這四個特性都為true

      要修改屬性的特性,必須使用Object.defineProperty()方法,這個方法接收三個參數,對象,屬性名和 特性名稱。

    訪問器屬性:

      訪問器屬性不包含數據值,它們包含一對getter和setter函數,在讀取訪問器屬性時,會調用getter,此函數會返回有效的值;在寫入訪問器屬性時,會調用setter並傳入新值,這個函數負責處理數據

      Configurable enumerable : 同數據屬性

      get: 讀取屬性時調用,

      set: 寫入屬性時調用

      在屬性名的前面加_ 表示 只能通過對象的方法訪問的屬性。

    定義多個屬性:

      Object.defineProperties () :

    讀取屬性的特性:

      Object.getOwnPropertyDescriptor () : 第一個參數為 指定的對象,第二個參數為要讀取描述符的屬性名;

2,創建對象

  1,工廠模式

  2,構造函數模式

    要創建實例,必須使用new操作符。以這種方式調用構造函數會經歷以下四個步驟: 1, 創建一個新對象; 2, 將構造函數的this指向新對象; 3,執行構造函數中的代碼; 4, 返回新對象。

     構造函數的問題是: 每個方法都要在每個實例上重新創建一遍,因為有this在,根本不用在執行代碼前就把函數綁定到特定的對象上。

  3,原型模式

    每個函數都有一個prototype屬性,這個指針指向該函數的原型對象。使用原型對象可以讓所有實例共享它所包含的屬性和方法

    可以通過實例去訪問保存在原型中的值,但不能通過對象實例重寫原型中的值。 調用Object.hasOwnProperty()可以檢查一個屬性是存在實例中還是存在原型中。

    for in循環的是所有能夠通過對象訪問的、可枚舉的屬性。既包含存在於實例的也包含存在於原型的屬性。

    Object.keys() : 獲取對象自身所有的可枚舉的屬性值,不包括原型的屬性,返回屬性組成的數組。

    Object.getOwnPropertyNames() : 獲取對象自身的所有屬性,包括不可枚舉的,不包括原型的。 返回組成的數組。

    原型對象的問題是: 所有屬性都是被實例共享的,那麽如果有一個引用類型的屬性,如果一個實例修改了,那麽所有實例的這個屬性都會修改。

  4,組合使用構造函數和原型對象

    實例屬性在構造函數中定義,方法在原型對象中定義。

  5,動態原型模式

    通過構造函數來初始化原型,通過判斷 原型中沒有,再添加。

  6,寄生構造函數模式

    在函數中new一個對象,將參數放入這個對象,返回這個對象。 這個對象和構造函數、構造函數的原型沒有任何關系。

  7,穩妥構造函數模式

    適合在安全的環境,不使用this,不使用new,返回一個對象,只能通過對外的接口來訪問其中的原始數據成員。 這個對象和構造函數

3,繼承

  1,原型鏈

    function Person(){}

    function Men () {}

    Men.prototype = new Person()

    Men.prototype.constructor = Men

    Men的實例查找一個屬性的時候,會先在實例上查找,如果沒有的話,就在實例的原型,也就是Men.prototype上查找,如果沒有,則會繼續沿著原型鏈向上,在Person的prototype上查找,如果沒有,則繼續向上,在Object.prototype上查找。

    確定原型和實例的關系

      1,使用instanceof : 只要實例與原型鏈中出現過的構造函數,都會返回true

      2,使用 isPrototypeOf() : 只要是原型鏈中出現過的原型,都會返回true

    謹慎的定義方法

      使用原型鏈繼承方法的時候,不能使用對象字面量創建原型方法,因為這樣會重寫原型鏈。

    原型鏈的問題

      因為在通過原型繼承的時候,原型會變成另一個類型的實例,那麽,原先的實例屬性就變成了現在的原型屬性了。 如果修改的話,會影響所有實例。

  2,借用構造函數

    子類的構造函數中, 使用 父類構造函數.call(this, ...args),此方法可以在子類構造函數中向超類構造函數傳遞參數。

    這種方法的問題是: 超類的原型 對子類來說是不可見的。

  3,組合繼承

    將原型鏈和借用構造函數的技術組合。

    function Person (name) { this.name = name}

    Person.prototype.sayName = function (){ console.log(this.name) }

    function Men (name) { Person.call(this, name) }

    Men.prototype = new Person()

    Men.prototype.constructor = Men

  4,原型式繼承

    

    

js高級程序設計 筆記 --- 面向對象的程序設計