JS繼承總結(小白友好篇)

繼承的本質: 子類繼承父類的屬性和方法。(目的是讓子類的實例能夠調取父類的屬性和方法。)markdown

ES5中的繼承

  • 原型繼承
    • 原理: 讓父類中的屬性和方法在子類實例的原型鏈上函數

      CHILD.prototype = new PARENT()ui

      CHILD.prototype.constrctor = CHILDthis

    • 特色:spa

      • 不像其餘語言同樣的繼承(其餘語言的繼承是拷貝繼承,會把父類的屬性和方法拷貝到子類中,供子類調取使用),它是把父類的實例放在子類實例的原型鏈上,實例想調取這些方法,是基於__proro__原型鏈查找機制完成的。
      • 子類能夠重寫父類上的方法,會致使父類其餘的實例也會收到影響。
      • 父類中私有或者公有的屬性方法,最後都會變成子類中公有方法。
// 原型鏈繼承舉🌰
// 父類
function Parent(x) {
    this.x = x
} 
Parent.prototye.getX = function() {
    console.log(this.x)
}
// 子類
function Child(y) {
    this.y = y
}
// 繼承
Child.prototype = new Parent('y') // 子類的原型指向父類的實例
Child.prototype.constrctor = Child // 保證子類構造函數的完整性
Child.prototype.getY = function() {
    console.log(this.y)
}
const child = new Child('x')
child.y // y 成功訪問子類屬性
child.x // x 成功訪問父類屬性
child.getX() // x 成功調用父類方法
child.getY() // y 成功調用子類自己方法

// 子類能夠經過 CHILD.prototype.__proto__修改父類,並對父類的其餘實例形成影響
Child.prototype.__proto__.other = function () {
    console.log('other')
}
const parent = new Parent(200)
parent.other() // other
複製代碼
  • CALL繼承
    • 原理:
      • 在CHILD方法中把PARENT方法看成普通函數來執行,讓PARENT中的this指向CHILD的實例,至關於給CHILD實例是設置了不少私有的屬性和方法
    • 特色:
      • 只能繼承父類私有的屬性和方法(由於是把PARENT看成普通函數執行,和其原型上的屬性和方法沒有關係)
      • 父類私有變爲子類私有
// CALL繼承舉🌰
// 父類
function Parent(x) {
    this.x = x
    this.thisGetX = function () {
        console.log(this.x)
    }
}
Parent.prototype.getX = function () {
    console.log(this.x)
}
// 子類
function Child(y) {
    // this => Child的實例
    Parent.call(this, 200)
    this.y = y
}
Child.prototype.getY = function () {
    console.log(this.y)
}

const child = new Child(100)
console.log(child.x) // 成功訪問父類屬性
child.getX() // 報錯 沒法訪問父類原型鏈上的屬性和方法
複製代碼
  • 寄生組合繼承
    • 原理: CALL繼承+蕾相似原型繼承
    • 特色:
      • 父類私有和公有的屬性、方法分別是子類實例的共同和私有方法(推薦)
// 寄生組合繼承舉🌰
// 父類
function Parent(x) {
    this.x = x
    this.thisGetX = function () {
        console.log(this.x)
    }
}
Parent.prototype.getX = function () {
    console.log(this.x)
}

// 子類
function Child(y) {
    // this => Child的實例
    Parent.call(this, 200)
    this.y = y
}

// Object.create => 建立一個空對象,讓空對象__proto__指向 Parent.prototype
Child.prototype = Object.create(Parent.prototype)
Child.prototype.constructor = Child
const child = new Child(100)
console.log(child.x) // 成功訪問父類屬性
child.getX() // 報錯 沒法訪問父類原型鏈上的屬性和方法

// 實現object.create方法
function create(obj) {
    function Fn() Fn.prototype = obj return new Fn() } 複製代碼

ES6中的繼承

  • class
    • 原理: class CHILD extends Parent {} => CHILD.prototype._ proto_ = PARENT.prototype
    • 特色:
      • 子類繼承父類能夠不屑constructor,一旦寫了,constructor內的第一句話必須是super(), super() 的做用相似call繼承。
// 父類
// ES6中基於class創造出來的類不能看成普通函數執行、不容許重定向原型的指向
class Parent {
    constructor(x) {
        this.x = x
    }
    getX() {
        console.log(this.x)
    }
}
// 子類
// class Child {
// constructor(y) {
// this.y = y
// }
// getY() {
// console.log(this.y)
// }
// }
// ES6中的繼承 
class Child extends Parent {
    constructor(y) {
        super(200)
        this.y = y
    }
    getY() {
        console.log(this.y)
    }
}
const child = new Child(100)
console.log(child.x) // 成功訪問父類屬性
child.getX() // 成功調用父類方法
複製代碼
相關文章
相關標籤/搜索