ES6中的繼承

一、基礎

  在ES6之前,主要靠構造函數和原型鏈的靈活使用實現繼承;而在ES6中引入了class(類)的概念,使得繼承更加方便,也更接近傳統的面嚮對象語言(C++,Java)中繼承的實現。
  ES6中類的定義如下:
 class Point {
        constructor(x, y) {
            this.x = x;
            this.y = y;
        }
        toString() {
            return '(' + this.x + ',' + this.y + ')';
        }
    }
   //測試用例
    var point = new Point(2, 3);
    console.log(point.toString());//(2,3)
    console.log(point.hasOwnProperty('x'));//true
    console.log(point.hasOwnProperty('y'));//true
    console.log(point.hasOwnProperty('toString'));//false
    console.log(point.__proto__.hasOwnProperty('toString'));//true

  以上代碼定義了一個‘類’,裏邊有一個constructor方法,這就是構造方法,this關鍵字代表實例對象。ES5中的構造函數Point,對應ES6中Point類的構造方法;
  constructor方法是類的默認方法,一個類必須有這個方法(如果沒有顯示定義,會默認添加constructor方法),通過new命令生成對象實例時,自動調用該方法;
  從以上的測試用例也可以看到:實例的屬性除非顯示定義在其本身(即:this對象上),否則都定義在原型上(這一特性和ES5一致);

二、Class的繼承

  基本用法:Class之間可以通過extends關鍵字實現繼承,這比ES5通過修改原型鏈實現繼承,要方便很多。
  示例程序如下:
  class Point {
        constructor(x, y) {
            this.x = x;
            this.y = y;
        }

        toString() {
            return '(' + this.x + ',' + this.y + ')';
        }
    }
    //繼承
    class ColorPoint extends Point {
        constructor(x, y, color) {
            super(x, y);
            this.color = color;
        }

        toString() {
            return this.color + ' ' + super.toString()
        }
    }
    var p = new ColorPoint(2, 3, 'red');
    console.log(p.toString());// red (2,3)

  以上代碼中,constructor方法和toString方法中,都出現了super關鍵字,這裏表示父類的構造函數,用來新建父類的this對象

注意:
  1、子類必須在constructor方法中調用super方法,否則新建實例會報錯(因爲子類沒有自己的this對象,而是繼承父類的this對象,然後對其進行再加工,如果不調用super方法,子類就得不到this對象);
  2、在子類的構造函數中,只有調用super之後才能用this關鍵字,否則會報錯。原因參考1;


類的prototype屬性和__proto__屬性

  在ES5中,每個對象都有__proto__屬性,指向構造函數的prototype屬性。Class作爲構造函數的語法糖,同時具有prototype屬性和__proto__屬性,所以存在兩條繼承鏈。
  1、子類的__proto__屬性,表示構造函數的繼承,總指向父類。
  2、子類的的prototype屬性的__proto__屬性,表示方法的繼承,總指向父類的prototype屬性。
  驗證如下:
 class A {
    }
 class B extends A {
    }
    console.log(B.__proto__ === A);//true
    console.log(B.prototype.__proto__ === A.prototype);//true



發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章