ES6里引入Class概念侮腹,非常類似其他面向?qū)ο笳Z言(比如Java)。實(shí)際上稻励,Class只是簡(jiǎn)化了對(duì)象原型方法的語法父阻,實(shí)現(xiàn)原理依舊是ES5構(gòu)造函數(shù)和對(duì)象原型。但是望抽,ES6中類的繼承加矛,和ES5原型鏈繼承略有不同。
1. Class語法
用ES6的class
定義類:
class Vehicle {
// 構(gòu)造函數(shù)
constructor(name) {
this.name = name;
}
// 實(shí)例方法
ignition() {
console.log("Start up:" + this.name);
}
// 靜態(tài)方法
static getType(){
console.log("Type: Vehicle");
}
static getName() {
console.log("Name: Vehicle");
}
// 靜態(tài)變量(ES7語法)
static defaultProps = {color: "red"};
// 存儲(chǔ)器屬性
set prop(value){
console.log("setter:" + value);
this.value= value;
}
get prop(){
return this.value;
}
}
var vehicle = new Vehicle ('vehicle');
vehicle.prop= 1; // setter:1
console.log(vehicle.prop); // 1
vehicle.ignition(); // "Start up:vehicle"
轉(zhuǎn)為ES5是:
function Vehicle (name) {
this.name = name;
}
// 實(shí)例方法
Vehicle.prototype.ignition = function () {
console.log("Start up:" + this.name);
}
// 靜態(tài)方法
Vehicle.getType = function (){
console.log("Type: Vehicle");
}
Vehicle.getName= function (){
console.log("Name: Vehicle");
}
// 靜態(tài)變量
Vehicle.defaultProps = {color: "red"};
用class
聲明的類的特點(diǎn)為:
- 所有方法都定義在原型屬性
Function.prototype
上煤篙。 - 必須有
constructor
方法斟览,如果沒有定義,會(huì)默認(rèn)添加一個(gè)空的構(gòu)造函數(shù)辑奈。 - 必須用
new
創(chuàng)建類的實(shí)例苛茂,否則會(huì)拋錯(cuò)TypeError("Cannot call a class as a function");
-
class
不存在變量提升。下面代碼會(huì)拋錯(cuò):
new Foo(); // TypeError: Foo is not a function
class Foo {};
2. 類的繼承:extend
延續(xù)上面的例子鸠窗,創(chuàng)建Vehicle
的子類Car
:
class Car extends Vehicle {
constructor(name){
super(name);
this.wheels = 4;
}
// 實(shí)例方法
drive(){
this.ignition();
console.log("Rolling on all "+this.wheels+"wheels!")
}
// 靜態(tài)方法
static getType(){
console.log("Type: Car");
}
}
var car = new Car('smart');
car.drive(); // Start up:smart
// 類實(shí)例無法訪問靜態(tài)方法
console.log(car.getType); //undefined
// 只有類本身可以調(diào)用靜態(tài)方法
Car.getType(); //Type: Car
ES6實(shí)現(xiàn)繼承的原理與ES5完全不同:
- ES5的繼承:先創(chuàng)建子類實(shí)例妓羊,然后將父類原型上的方法添加到子類實(shí)例上。
- ES6的繼承:先創(chuàng)建父類實(shí)例稍计,然后子類實(shí)例
this
指向父類this
躁绸,并且進(jìn)行修改。
正因?yàn)镋S6做繼承時(shí)臣嚣,是先創(chuàng)建父類實(shí)例净刮,因此,有如下兩個(gè)特性:
- 繼承時(shí)茧球,子類一旦顯性聲明了
constructor
函數(shù)庭瑰,就必須在構(gòu)造函數(shù)里面調(diào)用super()
方法,從而取得父類this
對(duì)象(也可以不顯性聲明constructor
函數(shù)抢埋,ES6會(huì)在默認(rèn)生成的構(gòu)造方法里面調(diào)用super()
)弹灭。 - 允許定義繼承原生數(shù)據(jù)結(jié)構(gòu)(Array, String等)的子類督暂,比如:
class myArray extends Array{
constructor(...args) {
super(...args);
}
}
var array = new myArray();
array.push(2);
array.length; //1
array[0]; //2
小結(jié)
在React中,實(shí)現(xiàn)組件用的就是ES6中class語法穷吮,例如:
import React from 'react';
export default class myTable extends React.Component {
constructor(props) {
super(props);
}
...
}
下一節(jié):ECMAScript6基礎(chǔ)學(xué)習(xí)教程(七)模塊