super这个关键词既可以当对象使用,也可以当函数使用
super作为函数使用
super作为函数使用时,只能在子类的构造函数中【目的是为了调用父类的构造函数】 => super表示父类构造函数,但是this指向当前子类的构造函数
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16
| class Father { constructor(name, age) { this.name = name; this.age = age; console.log(new.target.name); } }
class Son extends Father { constructor(name, age) { super(name, age); } }
new Father(); new Son();
|
在子类的constructor
中必须调用super()
方法,因为子类没有自己的this
对象,而是要继承父类的this
对象,但是此时this
指向的是子类的构造函数,此时super
就表示了父类的构造函数,super()
此时相当于Father.prototype.constructor.call(this, props)
super作为对象使用
super作为普通方法使用
(1)super指向的是父类的原型对象
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18
| class Father { static c() { return 1; }; c() { return 11; } constructor() {}; }
class Son extends Father { constructor() { super(); console.log(super.c()); } }
new Son();
|
在上面的代码中,子类中的super.c()
,就是把super
当作一个对象使用,对象里面有c
方法,因此super
在普通函数中指向,Father.prototype
,也就是说super.c()
相当于Father.prototype.c()
(2)通过super调用父类方法时,super内部的this指向子类的实例
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26
| class Father { x = 7; fun() { this.x = 77; }; print() { console.log(this.x); }; }
class Son extends Father { x = 777; fn() { super.fun(); this.x = 777; super.print(); } }
new Son().fn();
|
此时的super
可以替换this
,与this.print()
等价
(3)当通过super为子类属性赋值时,super就是this
1 2 3 4 5 6 7 8 9 10 11
| class Father {}
Father.prototype.c = 77;
class Son extends Father { fn() { super.c = 7; console.log(super.c); console.log(this.c); } }
|
赋值的情况下super
就是this
super作为静态方法使用
(1)super指向的是父类
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43
| class Father {}
Father.prototype.c = function() { return 11; }
class Son extends Father { fn() { super.c = function() { return 1 }; console.log(super.c()); console.log(this.c()); } }
new Son().fn();
class Father { static c() { console.log(2); } c() { console.log(22); } }
class Son extends Father { static s() { super.c(); } s() { super.c(); } }
Son.son(); new Son().c();
|
(2)在子类的静态方法中通过super调用父类方法是,super内部的this指向子类
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27
| class Father { static x = 3; constructor() { this.x = 2; }; static print() { console.log(this.x); } }
class Son extends Father { constructor() { super(); this.x = 4; } static fn() { this.x = 5; super.print(); } }
Son.x = 1; Son.fn();
|
例题
注意看注释~
1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28
| class Father { name = 'Father'; age = 18;
getName() { return this.name; } getAge() { return this.age; } }
class Son extends Father { constructor() { super(); } getAge() { return this.getAge() + 10; } } console.log(new Son().getName());
console.log(new Son().getAge.call({age:2}));
|
参考
理解 es6 class 中 constructor 方法 和 super 的作用
前端面试之关于super的全方位解读