在JavaScript中,继承的使用是比较常见的,尤其是在构建大型应用和复用代码时。JavaScript的继承主要通过原型链(Prototype Chain)和ES6引入的类(Class)语法来实现。
原型链继承:在JavaScript中,每个对象都有一个原型(prototype),当试图访问一个对象的属性时,如果该对象本身没有这个属性,就会去它的原型上找,这个过程会一直持续到找到该属性或者到达原型链的末端(null)。
类继承:ES6引入了类的概念,使得JavaScript的继承更加直观和易于理解。类继承通过extends
关键字实现,子类可以继承父类的属性和方法。
Object.create()
方法实现,适用于不需要构造函数的场景。class
和extends
关键字实现,语法简洁,易于理解。问题1:原型链继承中,所有子类实例共享父类的引用类型属性。
function Parent() {
this.arr = [1, 2, 3];
}
function Child() {}
Child.prototype = new Parent();
const child1 = new Child();
const child2 = new Child();
child1.arr.push(4);
console.log(child1.arr); // [1, 2, 3, 4]
console.log(child2.arr); // [1, 2, 3, 4],所有子类实例共享父类的引用类型属性
解决方法:使用组合继承或ES6类继承。
class Parent {
constructor() {
this.arr = [1, 2, 3];
}
}
class Child extends Parent {
constructor() {
super();
}
}
const child1 = new Child();
const child2 = new Child();
child1.arr.push(4);
console.log(child1.arr); // [1, 2, 3, 4]
console.log(child2.arr); // [1, 2, 3],每个子类实例拥有独立的引用类型属性
问题2:构造函数继承中,无法复用父类原型上的方法。
function Parent() {
this.sayHello = function() {
console.log('Hello');
};
}
function Child() {
Parent.call(this);
}
const child = new Child();
console.log(child.hasOwnProperty('sayHello')); // true,但无法复用父类原型上的方法
解决方法:使用组合继承或ES6类继承。
class Parent {
constructor() {
this.sayHello = function() {
console.log('Hello');
};
}
sayHi() {
console.log('Hi');
}
}
class Child extends Parent {
constructor() {
super();
}
}
const child = new Child();
console.log(child.hasOwnProperty('sayHello')); // true
child.sayHi(); // Hi,可以复用父类原型上的方法
通过以上方法和示例代码,可以有效地解决JavaScript继承中常见的问题。
领取专属 10元无门槛券
手把手带您无忧上云