JavaScript 繼承 - - 原型式繼承 & 對比 物件原型繼承 & 寄生式繼承
阿新 • • 發佈:2021-04-30
目錄
一、原型式繼承
2006年,Douglas Crockford在《JavaScript中的原型繼承》中提到:
function object(o){
function F(){ }; //臨時的建構函式,
F.prototype = o;
return new F();
}
我們來實踐一下這個方案:
// 原型式繼承:當傳入的引數為建構函式例項
// 寫一個工具函式 object
function object(o) {
function F() {};
F.prototype = o;
return new F();
}
//父建構函式
function Super() {
this.pbrand = 'super';
// 新增引用值
this.a = [1, 2, 3, 4, 5];
}
// 利用工具函式實現 :子 繼承 父
let suber1 = object(new Super());
let suber2 = object(new Super());
// 測試例項物件之間的屬性是否獨立:原始值
suber1.pbrand = 'suber' ;
console.log(suber1);
console.log(suber2);
// 測試例項物件之間的屬性是否獨立:引用值
suber1.a.push(8);
console.log(suber1);
console.log(suber2);
分析結果:
-
實現了子物件例項之間的原型上的引用值 b 還是共享的!
-
ECMAScript5 增加了Object.create() 將原型式繼承概念化,Object.create()與上面定義的object()效果相同
-
所以記住,原型上的屬性在例項之間是共享的,改變引用值屬性的話,會造成一變萬變
二、原型式繼承 與 物件原型繼承
- 從結果來看,這兩種繼承方式的效果都一樣
- 如果,不需要建立建構函式,然後實現繼承的話,原型式繼承就非常合適,
三、寄生式繼承
寄生式繼承背後的思路類似於寄生夠高函式和工廠模式:建立一個實現繼承的函式(這裡指create()),以某種方式增強物件,並返回這個物件
寄生式繼承仍存在prototype物件上引用值共享問題!
基本的寄生式繼承模式如下:
// 寄生式繼承
function object(o) {
function F() {};
F.prototype = o;
return new F();
}
// 繼承的工具函式:工廠模式
function create(obj) {
let o = object(obj);
return o;
}
let person = {
name: 'father',
friends: ['Jack', 'Rose']
}
let person1 = create(person);
let person2 = create(person);
person2.friends.push('Tom');
console.log(person1.friends);
console.log(person2.friends);