Ecmascript5 👉 Escmascript6 继承的变化"

👩🏿‍🎤 👩🏿‍🎤 👩🏿‍🎤 请用ES5的语法实现继承(extends):

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
function Parent(name, age) {
    this.name = name;
    this.age = age;
}

Parent.prototype.sayNameAndAge = function() {
    return `${this.name} is ${this.age} years old , he had better marry someone!`
}

function Child(name, age) {
    Parent.call(this, name, age);
}

Child.prototype = Object.create(Parent.prototype, {
    constructor: {
        value: Child,
        writable: true,
        enumerable: true,
        configurable: true,
    }
});

const tim = new Child('Tim', 18);
tim.sayNameAndAge();

① 在Child构造函数内部,通过Parent.call(this)来初始化子类的实例属性,因为没有必要this.name = name;this.age = age;这样写,过于繁琐了。

② Object.create方法返回一个对象,我们通过Object.create来指定返回的对象的prototype,Object.create的第二个参数可以定义这个对象的属性,上面指定了constructor属性,因为Object.create返回的对象没有constructor属性,所以我们将constructor属性指向Child函数。

👩🏿‍🎤 👩🏿‍🎤 👩🏿‍🎤 那你能用ES6的class特性实现一个继承吗?

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
16
17
18
19
class Parent {
    constructor(name, age) {
        this.name = name;
        this.age = age;
    }

    sayNameAndAge() {
        return `${this.name} is ${this.age} years old , he had better marry someone!`
    }
}

class Child extends Parent {
    constructor(name, age) {
        super(name, age);
    }
}

const tim = new Child('Tim', 18);
tim.sayNameAndAge();

观察到代码量明显地减少,但这没什么了不起的,只是语法糖而已,底层还是原型继承的原理。

👩🏿‍🎤 👩🏿‍🎤 👩🏿‍🎤 你知道静态方法/属性吧?他们如何被继承

ES6的extends操作在底层会把父类的静态方法/属性复制给子类,我无需做什么:

 1
 2
 3
 4
 5
 6
 7
 8
 9
10
11
12
13
14
15
class Parent {
    static age = 18;
    static name = 'Tim';
    static getNameAndAge() {
        console.log('静态方法被调用')
    }
}

class Child extends Parent {

}

console.log(Child.age);
console.log(Child.name);
Child.getNameAndAge();

👩🏿‍🎤 👩🏿‍🎤 👩🏿‍🎤 extends 后面只能是用class声明的类吗,还有其他的吗?

神奇的就在于extends竟然可以继承函数(除了箭头函数),其实也不难理解,使用typeof查看class的类型返回的是function。但最重要的原因是类和函数都具有内部属性👉[[construct]]。

updatedupdated2020-07-162020-07-16