ES6 學習筆記

介紹

ECMAScript 6 在接下來的一段時間內將成爲 ECMAScript的一個標準。這個標準預計在今年的時候就會被簽署,無論在Github,仍是在不少社區,javascript愛好者已經早已開始擁抱變化,享受ES6 帶來的美好,這篇文章將介紹ES6的一些新特性。因爲ES6 尚未很好地被瀏覽器支持,因此這篇文章的ES6代碼將使用 Babel 進行編譯。javascript

ECMAScript 6 的新特性

箭頭(Arrow)

=> 是function的簡寫形式,支持expressionstatement 兩種形式。同時一點很重要的是它擁有詞法做用域的this值,幫你很好的解決this的指向問題,這是一個很酷的方式,能夠幫你減小一些代碼的編寫,先來看看它的語法。java

([param] [, param]) => {
   statements
}

param => expression

而後再來看看例子,以及babel 編譯後的結果。git

ES6:github

clipboard.png

babel編譯後結果:express

clipboard.png

類(class)

ES6 引入了class(類),讓javascript的面向對象編程變得更加容易清晰和容易理解。類只是基於原型的面向對象模式的語法糖。編程

class Animal {
    // 構造方法,實例化的時候將會被調用,若是不指定,那麼會有一個不帶參數的默認構造函數.
    constructor(name,color) {
      this.name = name;
      this.color = color;
    }
    // toString 是原型對象上的屬性
    toString() {
      console.log('name:' + this.name + ',color:' + this.color);

    }
  }
   
 var animal = new Animal('dog','white');
 animal.toString();

 console.log(animal.hasOwnProperty('name')); //true
 console.log(animal.hasOwnProperty('toString')); // false
 console.log(animal.__proto__.hasOwnProperty('toString')); // true

 class Cat extends Animal {
  constructor(action) {
    // 子類必需要在constructor中指定super 方法,不然在新建實例的時候會報錯.
    // 若是沒有置頂consructor,默認帶super方法的constructor將會被添加、
    super('cat','white');
    this.action = action;
  }
  toString() {
    console.log(super.toString());
  }
 }

 var cat = new Cat('catch')
 cat.toString();
 
 // 實例cat 是 Cat 和 Animal 的實例,和Es5徹底一致。
 console.log(cat instanceof Cat); // true
 console.log(cat instanceof Animal); // true

類的 prototype 屬性和 __proto__ 屬性

在上一篇 javascript面向對象編程 中咱們已經瞭解到一個實例化對象會有一個 __proto__ 指向構造函數的 prototype 屬性。在 class 中。同時具備 __proto__prototype 兩個屬性,存在兩條繼承鏈。segmentfault

  • 子類的 __proto__ 屬性,表示構造函數的繼承,老是指向父類。瀏覽器

  • 子類的 prototype 的 __proto__ 屬性表示方法的繼承,老是指向父類的 prototype 屬性。babel

class Cat extends Animal {}
  console.log(Cat.__proto__ === Animal); // true
  console.log(Cat.prototype.__proto__ === Animal.prototype); // true

咱們先來看第一條 Cat.__proto__ === Animal 這條原型鏈。完成構造函數繼承的實質以下:模塊化

class Cat extends Animal {
   construcotr() {
     return Animal.__proto__.call(this);
  }
 }

第二條對原型鏈 Cat.prototype.__proto__ === Animal.prototype 完成方法的繼承,實質以下:

Cat.prototype.__proto__ = Animal.prototype

另外還有還有三種特殊狀況。

class A extends Object {}
 console.log(A.__proto__ === Object); // true
 console.log(A.prototype.__proto__ === Object.prototype);

A繼承Object,A的__prototype__ 指向父類Object. A的 prototype.__proto__ 指向父類Object的prototype。

從上篇文章中的 函數對象的原型 中咱們能夠了解到,函數是一種特殊的對象,全部函數都是 Function 的實例。

class Cat {}
 console.log(Cat.__proto__ === Function.prototype); //true
 console.log(Cat.prototype.__proto__ === Object.prototype); //true

因爲Cat不存在任何繼承,就至關於一個普通函數,因爲函數都是Function 的實例,因此 Cat.__proto__指向 Function.prototype. 第二條繼承鏈指向父類(Function.prototype) 的prototype屬性,因此 Cat.prototype.__proto__ === Object.prototype. Cat調用後會返回Object實例,因此 A.prototype.__proto__ 指向構造函數(Object)的prototype。

class Cat extends null {};
 console.log(Cat.__proto__ === Function.prototype); // true;
 console.log(Cat.prototype.__proto__ === null); //true

Cat是一個普通函數,因此繼承 Function.prototype .第二條繼承鏈不繼承任何方法,因此 Cat.prototype.__proto__ == null.

Module

到目前爲止,javascript (ES5及之前) 還不能支持原生的模塊化,大多數的解決方案都是經過引用外部的庫來實現模塊化。好比 遵循CMD規範的 Seajs 和AMD的 RequireJS 。在ES6中,模塊將做爲重要的組成部分被添加進來。模塊的功能主要由 exportimport 組成.每個模塊都有本身單獨的做用域,模塊之間的相互調用關係是經過 export 來規定模塊對外暴露的接口,經過import來引用其它模塊提供的接口。同時還爲模塊創造了命名空間,防止函數的命名衝突。

export,import 命令

//test.js
  export var name = 'Rainbow'

ES6將一個文件視爲一個模塊,上面的模塊經過 export 向外輸出了一個變量。一個模塊也能夠同時往外面輸出多個變量。

//test.js
 var name = 'Rainbow';
 var age = '24';
 export {name, age};

定義好模塊的輸出之後就能夠在另一個模塊經過import引用。

//index.js
 import {name, age} from './test.js'

總體輸入,module指令

//test.js
  
  export function getName() {
    return name;
  }
  export function getAge(){
   return age;
  }

經過 import * as 就完成了模塊總體的導入。

import * as test form './test.js';

經過指令 module 也能夠達到總體的輸入。

module test from 'test.js';
 test.getName();

export default

不用關係模塊輸出了什麼,經過 export default 指令就能加載到默認模塊,不須要經過 花括號來指定輸出的模塊,一個模塊只能使用 export default 一次

// default 導出
  export default function getAge() {} 
 
  // 或者寫成
  function getAge() {}
  export default getAge;

  // 導入的時候不須要花括號
  import test from './test.js';

一條import 語句能夠同時導入默認方法和其它變量.

import defaultMethod, { otherMethod } from 'xxx.js';
相關文章
相關標籤/搜索