JavaScript inheritance patterns primarily include the following:
1. Prototype Chain Inheritance
Prototype chain inheritance is the most fundamental inheritance method in JavaScript. Every JavaScript object has a prototype (prototype), and objects inherit properties and methods from their prototype. When creating a subclass, set the subclass's prototype to an instance of the parent class to achieve inheritance.
javascriptfunction Parent() { this.parentProperty = true; } Parent.prototype.getParentProperty = function() { return this.parentProperty; }; function Child() { this.childProperty = false; } Child.prototype = new Parent(); // Set Child's prototype to an instance of Parent Child.prototype.constructor = Child; // Correct the constructor reference var childInstance = new Child(); console.log(childInstance.getParentProperty()); // true
Issues with prototype chain inheritance include: inability to pass parameters to the parent constructor when creating subclass instances, and all instances sharing reference properties from the parent constructor.
2. Constructor Inheritance
Constructor inheritance enhances subclass instances by invoking the parent constructor within the subclass constructor using call or apply methods.
javascriptfunction Parent(name) { this.name = name; this.colors = ['red', 'blue', 'green']; } function Child(name) { Parent.call(this, name); // Invoke parent constructor within subclass constructor } var childInstance = new Child('ChildName'); console.log(childInstance.name); // ChildName
This approach allows distinct properties across subclass instances. However, it cannot inherit methods defined on the parent's prototype, so it is not true inheritance.
3. Combination Inheritance
Combination inheritance integrates prototype chain inheritance for methods and constructor inheritance for instance properties.
javascriptfunction Parent(name) { this.name = name; this.colors = ['red', 'blue', 'green']; } Parent.prototype.sayName = function() { return this.name; }; function Child(name, age) { Parent.call(this, name); // Borrow parent constructor to inherit properties this.age = age; } Child.prototype = new Parent(); // Prototype chain inheritance for methods Child.prototype.constructor = Child; var childInstance = new Child('ChildName', 18); console.log(childInstance.sayName()); // ChildName console.log(childInstance.age); // 18
Combination inheritance resolves the limitations of both prototype chain and constructor inheritance, but it invokes the parent constructor twice, resulting in unnecessary performance overhead.
4. Prototypal Inheritance
Prototypal inheritance uses an existing object as the prototype for a new object. ES5 introduced the Object.create method to implement this pattern.
javascriptvar parent = { name: 'Parent', sayName: function() { return this.name; } }; var child = Object.create(parent); child.name = 'Child'; console.log(child.sayName()); // Child
This approach is concise, but all instances share reference properties.
5. Parasitic Inheritance
Parasitic inheritance extends prototypal inheritance by adding additional properties or methods.
javascriptvar parent = { name: 'Parent', sayName: function() { return this.name; } }; function createAnother(original) { var clone = Object.create(original); clone.sayHi = function() { console.log('Hi'); }; return clone; } var child = createAnother(parent); child.sayHi(); // Hi