ES6代碼
class Point {
x: number;
y: number;
constructor(x: number, y: number) {
this.x = x;
this.y = y;
}
}
class Point3D extends Point {
z: number;
constructor(x:number, y:number, z: number) {
super(x,y)
this.z = z;
}
}
編譯
var __extends = (this && this.__extends) || (function () {
var extendStatics = function (d, b) {
extendStatics = Object.setPrototypeOf ||
({ __proto__: [] } instanceof Array && function (d, b) { d.__proto__ = b; }) ||
function (d, b) { for (var p in b) if (b.hasOwnProperty(p)) d[p] = b[p]; };
return extendStatics(d, b);
};
return function (d, b) {//參數(shù)d是derive(派生)的簡寫凡傅,參數(shù)b是base的簡寫
extendStatics(d, b);//繼承靜態(tài)成員
function __() { this.constructor = d; }
d.prototype = b === null ? Object.create(b) : (__.prototype = b.prototype, new __());
};
})();
var Point = /** @class */ (function () {
function Point(x, y) {
this.x = x;
this.y = y;
}
return Point;
}());
var Point3D = /** @class */ (function (_super) {
__extends(Point3D, _super);
function Point3D(x, y, z) {
// _super.call()用于繼承基類的屬性成員
var _this = _super.call(this, x, y) || this;
_this.z = z;
return _this;
}
return Point3D;
}(Point));
分析
結(jié)合《JavaScript高級程序設(shè)計(jì)》6.3節(jié)繼承中所說,在子類構(gòu)造函數(shù)的內(nèi)部調(diào)用基類構(gòu)造函數(shù)帐偎,即_super.call(this, x, y)
脊岳。這樣在創(chuàng)建子類Point3D
實(shí)例的時(shí)候就會執(zhí)行基類構(gòu)造函數(shù)的代碼,獲取基類屬性私股。
在__extends
函數(shù)中主要做了兩件事:
- 將基類的靜態(tài)成員賦值到子類。即
extendStatics
函數(shù)實(shí)現(xiàn)的功能恩掷。 - 設(shè)置子類函數(shù)的原型
針對第二點(diǎn)倡鲸,簡化代碼如下
function __() { this.constructor = d; }
__.prototype = b.prototype
d.prototype = new __();
如上代碼的最終目的就是d.prototype.__proto__ = b.prototype
。
通過第3行代碼可以看出d.prototype = {__proto__: __.prototype }
結(jié)合第2行代碼黄娘,可知d.prototype = {__proto__ : b.prototype}
因此可以獲知最終結(jié)果d.prototype.__proto__ = b.prototype
峭状。
第一行代碼作用是需要保留原始d.prototype.constructor
。
終極結(jié)果就是d.prototype = {__proto__: b.prototype, constructor: d}
逼争。
小結(jié):這里的function __(){}
作為中轉(zhuǎn)函數(shù)优床,將原型鏈傳遞下去。使用結(jié)合繼承的方式繼承了普通屬性誓焦,靜態(tài)屬性和函數(shù)胆敞。