function SuperType(){ this.property = true; } SuperType.prototype.getSuperValue = function(){ return this.property; }; function SubType(){ this.subproperty = false; } // 繼承了 SuperType SubType.prototype = new SuperType(); var subType = new SubType(); console.log(subType.getSuperValue()); // 繼承了 SuperType 的 getSuperValue 方法,打印 true
function SuperType(){ this.colors = ["red", "blue", "green"]; } function SubType(){ } // 繼承了 SuperType SubType.prototype = new SuperType(); var subType1 = new SubType(); subType1.colors.push("black"); // subType1 修改 colors console.log(subType1.colors); // "red,blue,green,black" var subType2 = new SubType(); console.log(subType2.colors); // "red,blue,green,black",subType2 的 colors 值爲 subType1 修改以後的值
function SuperType(){ this.colors = ["red", "blue", "green"]; } function SubType(){ // 繼承了 SuperType SuperType.call(this); // 經過 apply() 或 call() 執行 SuperType 的構造函數 } var instance1 = new SubType(); instance1.colors.push("black"); alert(instance1.colors); // "red,blue,green,black" var instance2 = new SubType(); alert(instance2.colors); // "red,blue,green"
該方法解決了 原型鏈繼承
的引用型屬性共享的問題。javascript
還有能夠在子類型構造函數中向超類型構造函數傳遞參數,以下例子:java
function SuperType(name){ this.name = name; } function SubType(){ // 繼承 SuperType,並傳遞參數 SuperType.call(this, "Nicholas"); // 實例屬性 this.age = 29; } var subType = new SubType(); console.log(subType.name); //"Nicholas"; console.log(subType.age); //29
function SuperType(name){ this.name = name; this.colors = ["red", "blue", "green"]; } SuperType.prototype.sayName = function(){ console.log(this.name); }; function SubType(name, age){ // 執行 SuperType 的構造函數,繼承 SuperType 的屬性 SuperType.call(this, name); this.age = age; } // 將 SuperType 的實例賦給 SubType 的原型對象,這樣 SubType 可繼承 SuperType 原型中的方法 SubType.prototype = new SuperType(); SubType.prototype.sayAge = function(){ console.log(this.age); }; var subType1 = new SubType("Nicholas", 29); subType1.colors.push("black"); console.log(subType1.colors); // "red,blue,green,black" subType1.sayName(); // "Nicholas"; subType1.sayAge(); // 29 var subType2 = new SubType("Greg", 27); console.log(subType2.colors); // "red,blue,green" subType2.sayName(); // "Greg"; subType2.sayAge(); // 27
該方法基於已有的對象建立新對象,同時還沒必要所以建立自定義類型。數組
var person = { name: "Nicholas", friends: ["Shelby", "Court", "Van"] }; var anotherPerson = Object.create(person); // 使用 person 做爲新對象(anotherPerson)的原型 anotherPerson.name = "Greg"; anotherPerson.friends.push("Rob"); var yetAnotherPerson = Object.create(person); yetAnotherPerson.name = "Linda"; yetAnotherPerson.friends.push("Barbie"); console.log(person.friends); // "Shelby,Court,Van,Rob,Barbie"
該方法建立一個僅用於封裝繼承過程的函數,該函數在內部以某種方式來加強對象,最後再像真地是它作了全部工做同樣返回對象。app
function creatAnother(original) { var clone = Object.create(original); // 建立一個新對象 clone.sayHi = function() { // 以某種方式來加強這個對象 console.log("hi"); } return clone; // 返回該對象 } // 使用示例 var person = { name: "Nicholas", friends: ["Shelby", "Court", "Van"] }; var anotherPerson = creatAnother(person); anotherPerson.sayHi(); // "hi"
該方法解決原型鏈/構造函數組合繼承調用兩次超類型構造函數的問題。函數
經過借用構造函數來繼承屬性,經過原型鏈的混成形式來繼承方法。其背後的基本思路是:沒必要爲了指定子類型的原型而調用超類型的構造函數,咱們所須要的無非就是超類型原型的一個副本而已。本質上,就是使用寄生式繼承來繼承超類型的原型,而後再將結果指定給子類型的原型。this
function object(o){ function F(){} F.prototype = o; return new F(); } function inheritPrototype(subType, superType){ var prototype = object(superType.prototype); // 根據超類型原型建立新對象 prototype.constructor = subType; // 將新對象的 constructor 設置爲子類型 subType.prototype = prototype; // 將新對象賦給子類型的原型 } function SuperType(name){ this.name = name; this.colors = ["red", "blue", "green"]; } SuperType.prototype.sayName = function(){ console.log(this.name); }; function SubType(name, age){ SuperType.call(this, name); this.age = age; } inheritPrototype(SubType, SuperType); SubType.prototype.sayAge = function(){ console.log(this.age); }; var subType1 = new SubType("Nicholas", 29); subType1.colors.push("black"); console.log(subType1.colors); // "red,blue,green,black" subType1.sayName(); // "Nicholas"; subType1.sayAge(); // 29 var subType2 = new SubType("Greg", 27); alert(subType2.colors); // "red,blue,green" subType2.sayName(); // "Greg"; subType2.sayAge(); // 27
參考資料:《JavaScript高級程序設計(第3版)》第6.3節 繼承prototype