继承

继承 属于 JavaScript

1 个练习

关于 继承

继承是一种在类之间建立父子关系的方式。 子类(有时也称为派生类)可以访问父类(有时也称为基类)定义的行为和数据。

class Pet {
  constructor(name) {
    this.name = name;
  }

  introduce() {
    console.log(`This is my pet, ${this.name}.`);
  }
}

class Dog extends Pet {}

const dog = new Dog('Otis');
dog.introduce();
// => This is my pet, Otis.

子类声明中的extends关键字通过原型链与父类建立联系。

由子类构造函数创建的对象,其原型链中会包含父类的原型,因此可以访问父类定义的任何方法或数据。

const dog = new Dog('Otis');

Dog.prototype.isPrototypeOf(dog); // => true
Pet.prototype.isPrototypeOf(dog); // => true
Pet.prototype.isPrototypeOf(Dog.prototype); // => true

Pet.prototype.hasOwnProperty('introduce'); // => true
Dog.prototype.hasOwnProperty('introduce'); // => false
dog.hasOwnProperty('introduce'); // => false

构造函数

如果子类没有定义构造函数,就会使用父类的构造函数。 但如果子类定义了自己的构造函数,就必须显式调用父类的构造函数。 要在子类构造函数内部调用父类构造函数,需要使用关键字super。

class Pet {
  constructor(name) {
    this.name = name;
  }
}

class Dog extends Pet {
  constructor(name, breed) {
    super(name);
    this.breed = breed;
  }
}

const dog = new Dog('Otis', 'Pug');

由于父类构造函数负责初始化新对象并将其赋值给this,因此必须在子类构造函数使用this之前就调用它。

class Dog extends Pet {
  constructor(name, breed) {
    // using 'this' before calling the parent constructor with 'super'
    this.breed = breed;
    super(name);
  }
}

const dog = new Dog('Otis', 'Pug');
// => ReferenceError: Must call super constructor in derived class before accessing 'this'...

在子类上定义方法

除了从父类继承的行为之外,子类还可以定义自己的行为。

这是使用继承的主要原因之一:让特定的子类拥有自己独有的数据和方法,同时通过父类提供的共享方法和数据彼此关联。

class Dog extends Pet {
  constructor(name, breed) {
    super(name);
    this.breed = breed;
  }

  describe() {
    console.log(`${this.name} is a ${this.breed}.`);
  }
}

const dog = new Dog('Otis', 'Pug');
dog.introduce();
dog.describe();
// => 'This is my pet, Otis.'
// => 'Otis is a Pug.'

重写从父类继承的方法

子类还可以重写父类定义的方法的行为,用子类定义的行为来替换或扩展它。

class Cat extends Pet {
  // replacing parent class behavior
  introduce() {
    console.log(`This is my cat, ${this.name}.`);
  }
}

class Dog extends Pet {
  constructor(name, breed) {
    super(name);
    this.breed = breed;
  }

  describe() {
    console.log(`${this.name} is a ${this.breed}.`);
  }

  // extending parent class behavior
  introduce() {
    super.introduce();
    this.describe();
  }
}

const cat = new Cat('Milo');
cat.introduce();
// => 'This is my cat, Milo.'

const dog = new Dog('Otis', 'Pug');
dog.introduce();
// => This is my pet, Otis.
// => Otis is a Pug.

如果要在子类中同名方法的方法体里调用父类定义的方法,必须使用关键字super来引用父类。

通过 GitHub 编辑 该链接会在新窗口或标签页中打开

学习 继承