2016年7月4日

[筆記] 談談JavaScript ES6中的Classes


由於class的用法在許多程式語言中都相當普遍,因此在最新的ES6中也會添加Class的用法,然而,這種用法雖然是使用class,但實際上和classical inheritance仍然是不一樣的!在JavaScript中仍然是使用prototypal inheritance的方法。



class的這種做法在JavaScript實際上只是syntax sugar,也就是說,它只是用來建立物件和原型的另一種撰寫方式,但背後運作的邏輯其實和 function constructor 或者是 Object.create 還是一樣的。

類別宣告(class declaration) - class, constructor


讓我們來看一下可以怎麼使用class,使用的方法如下:

class Person{
    constructor(firstname, lastname){
        this.firstname = firstname;
        this.lastname = lastname;
    }
    
    getFullName(){
        return "Hello "+ this.firstname + " " + this.lastname;
    }
}

var john = new Person("John","Doe");
console.log(john);


在class中,我們可以使用 constructor 來建立物件,同時,我們也可以在class中放入方法,最後一樣透過 new 這個關鍵字,我們就可以建立john這個物件。要注意的是,在一個class中,只能有一個constructor。

在JavaScript中雖然和其他程式一樣使用了class這個關鍵字,但要注意的是class裡面所建立的內容仍然是個物件。

建立子類別 - extends


接著讓我們看看如何用class裡面的方法來建立子類別:


//  code from MDN
class Animal{
    constructor(name){
        this.name = name;
    }

    speak(){
        return this.name + ' makes a noise';
    }
}

class Dog extends Animal{
    speak(){
        return this.name + ' makes a bark';
    }
}

var ruby = new Dog("Ruby");
console.log(ruby);
ruby.speak();


這裡我們一共建立了兩個類別,其中一個是Animal,另一個是Dog。我們可以透過 extends 這個關鍵字,使得Dog是Animal的子類別。

如果我們輸入 ruby.speak( ) 則會出現 "Ruby makes a bark"。

在Chrome的 console 視窗中,我們可以輸入 ruby.__proto__ 這樣的方式來看出 ruby 這個物件的整個prototypal chain ,當我們輸入 speak 的時候,因為在ruby這個物件中並找不到speak這個方法,因此會往它的 prototype 去找,如果找到的話,就會停在這裡,但如果還是找不到的話,則會繼續往裡面的prototype找,直到undefined為止。


呼叫父類別 - super


最後,如果我們想要在子類別中,呼叫父類別的方法來使用,可以透過 super 這個關鍵字:

//  modify code from MDN
class Animal{
    constructor(name){
        this.name = name;
    }

    speak(){
        return this.name + ' makes a noise';
    }
}

class Dog extends Animal{
    speak(){
        return this.name + ' makes a bark';
    }
    speakAnimal(){
        return super.speak();
    }
}

var ruby = new Dog("Ruby");
console.log(ruby.speak());    //    Ruby makes a bark
console.log(ruby.speakAnimal();    //    Ruby makes a noise


如此,我們就可以得到"Ruby makes a bark"和"Ruby makes a noise"。

程式範例

//  class declaration
class Person{
    constructor(firstname, lastname){
        this.firstname = firstname;
        this.lastname = lastname;
    }
    
    getFullName(){
        return "Hello "+ this.firstname + " " + this.lastname;
    }
}

var john = new Person("John","Doe");
console.log(john);

//  modify code from MDN
class Animal{
    constructor(name){
        this.name = name;
    }

    speak(){
        return this.name + ' makes a noise';
    }
}

class Dog extends Animal{
    speak(){
        return this.name + ' makes a bark';
    }
    speakAnimal(){
        return super.speak();
    }
}

var ruby = new Dog("Ruby");
console.log(ruby.speak());
console.log(ruby.speakAnimal());


→回到此系列文章目錄



0 意見:

張貼留言