Neues Node.js-Buch
Alle Artikel

Apply pseudoclassical inheritance

Problem

You want to use pseudoclassical inheritance, i.e., create a “class” as “subclass” of another “class”.

Ingredients

  • 2 or more functions
  • the prototype property
  • the call() method

Directions

  1. Define a function intended to be a constructor function (this will be the “superclass”).

    function Animal(color) {
      this._color = color;
    }
  1. Define some properties and/or methods on the prototype of that function. Those are the members of the “class”.

    function Animal(color) {
      this._color = color;
    }
    Animal.prototype.getColor = function() {
      return this._color;
    }
    Animal.prototype.makeSound = function() {
      console.log('Generic animal cannot make any sound.');
    }
  2. Define another function intended to be a constructor function based on the previously defined function (this will be the “subclass”).

    ...
    function Dog(name, color) {
      this._name = name;
    }
  3. Set the prototype property of that function.

    ...
    function Dog(name, color) {
      this._name = name;
    }
    Dog.prototype = new Animal();
  4. Call the super constructor function using the call() method, passing this and the parameters expected by the super constructor.

    ...
    function Dog(name, color) {
      Animal.call(this, color);
      this._name = name;
    }
    Dog.prototype = new Animal();
  5. Define some properties and/or methods on the prototype of that function.

    ...
    function Dog(name, color) {
      Animal.call(this, color);
      this._name = name;
    }
    Dog.prototype = new Animal();
    Dog.prototype.getName = function() {
      return this._name;
    }
  6. Optional: overwrite methods by defining them on the prototype of the “subclass”.

    ...
    function Dog(name, color) {
      Animal.call(this, color);
      this._name = name;
    }
    Dog.prototype = new Animal();
    Dog.prototype.getName = function() {
      return this._name;
    }
    Dog.prototype.makeSound = function() {
      console.log('Wuff wuff');
    }
  7. Voilá, there you got a perfect pseudoclassical inheritance.

    function Animal(color) {

      this._color = color;

    }
    
Animal.prototype.getColor = function() {

      return this._color;
    }

    Animal.prototype.makeSound = function() {

      console.log('Generic animal cannot make any sound');
    
}
    function Dog(name, color) {
      Animal.call(this, color);
      this._name = name;
    }
    Dog.prototype = new Animal();
    Dog.prototype.getName = function() {
      return this._name;
    }
    Dog.prototype.makeSound = function() {
      console.log('Wuff wuff');
    }
    
    var dog = new Dog('Bello', 'brown');
    console.log(dog.getName());            // "Bello"
    console.log(dog.getColor());           // "brown"
    console.log(dog instanceof Dog);       // true
    console.log(dog instanceof Animal);    // true
    dog.makeSound();                       // "Wuff wuff"
    var animal = new Animal('yellow');
    console.log(animal.getColor());        // "yellow"
    console.log(animal instanceof Animal); // true
    console.log(animal instanceof Dog);    // false
    animal.makeSound();                    // "Generic animal cannot make any sound."

Alternative recipes

  • Use prototypical inheritance, which is more natural to the language JavaScript.
  • Since ES2015: use class syntax, which is syntactic sugar for pseudoclassical inheritance.

    class Animal {
      ...
    }
    class Dog extends Animal {
      ...
    }