How much do you know about JavaScript inheritance?

How much do you know about JavaScript inheritance?

Preface

How much do you know about inheritance? What kind of inheritance is the best? Let's learn some knowledge points about inheritance and show you their implementation process, as well as their advantages and disadvantages.

The relationship between constructor, prototype object, and instance object

Understanding their relationship first will help you better understand inheritance

Prototype chain inheritance

Core: Use parent class instance as subclass prototype

Code implementation process:

function Parent(name){
    this.name = name || 'xt',
    this.arr = [1]
}
function Son(age){
    this.age = age
}
Parent.prototype.say = function() { //Define the methods that need to be reused and shared on the parent class prototype console.log('hello');
}
Son.prototype = new Parent()
let s1 = new Son(18)
let s2 = new Son(19)
console.log(s1.say() === s2.say()); //true
console.log(s1.name,s1.age); //xt 18
console.log(s2.name,s2.age); //xt 19
s1.arr.push(2)
console.log(s1.arr,s2.arr); // [ 1, 2 ] [ 1, 2 ]

advantage:

The attributes that an instance can inherit are: the attributes of the instance's constructor, the attributes of the parent class constructor, and the attributes of the parent class prototype. (The new instance does not inherit the properties of the parent class instance!)

shortcoming:

  • The subclass instance shares the reference properties of the parent class constructor, such as the arr property (the properties on the prototype are shared, and if one instance modifies the prototype property, the prototype property of the other instance will also be modified!)
  • Cannot pass parameters to parent class constructor

Borrowing constructor inheritance

Core: Use the parent class's constructor to enhance the child class instance, which is equivalent to copying the parent class's instance attributes to the child class.

Code implementation:

function Parent(name) {
    this.name = name;
    this.arr = [1],
    this.say = function() { console.log('hello') }
}
function Son(name, age) {
    Parent.call(this, name) //Copies the instance properties and methods of the parent class this.age = age
}
let s1 = new Son('小谭', 18)
let s2 = new Son('Xiaoming', 19)
console.log(s1.say === s2.say) //false Methods cannot be reused. Methods are independent, not shared. console.log(s1.name, s1.age); //Xiao Tan 18
console.log(s2.name, s2.age); //Xiaoming19
s1.arr.push(2)
console.log(s1.arr, s2.arr); // [ 1, 2 ] [ 1 ]

advantage:

  • It only inherits the properties of the parent class constructor, not the properties of the parent class prototype.
  • Can inherit multiple constructor properties (call multiple)
  • In the child instance, parameters can be passed to the parent instance.

shortcoming:

  • Can only inherit properties from the parent class constructor.
  • Constructor reuse is not possible. (You need to call it again each time you use it)
  • Each new instance has a copy of the parent class constructor, which is bloated.

Prototypal inheritance

Core: Wrap an object with a function and return the call of this function. This function becomes an instance or object that can add attributes at will.

function Parent(name) {
    this.name = 'xt';
    this.arr = [1]
}
function object(obj){
    function F(){}
    F.prototype = obj;
    return new F();
  }
let s1 = new Parent(object)
s1.name = 'Xiaoming'
s1.arr.push(2)
let s2 = new Parent(object)
console.log(s1.name,s2.name); // Xiaoming xt
console.log(s1.arr, s2.arr); //[ 1, 2 ] [ 1 ]

shortcoming:

  • All instances inherit the properties of the prototype and cannot pass parameters.
  • Reuse is not possible. (New instance attributes are added later)

Parasitic inheritance

Core: Based on prototype inheritance, enhance the object and return the constructor

function Parent(name) {
    this.name = 'xt';
    this.arr = [1]
}
function object(obj){
    function F(){}
    F.prototype = obj;
    return new F();
  }
let Son = new Parent()
function addobject(obj){
    var add = object(obj)
    add.name = 'Xiaobai'
    return add
}
var s1 = addobject(Son)
console.log(s1.name); //Xiaobai

shortcoming:

  • The prototype is not used and cannot be reused.
  • The reference type properties of multiple instances inherited by the prototype chain point to the same thing, which may lead to tampering.

Combined inheritance (combined prototype chain inheritance and borrowed constructor inheritance)

Core: By calling the parent class constructor, the properties of the parent class are inherited and the advantages of parameter passing are retained; then, by using the parent class instance as the subclass prototype, function reuse is achieved.

Code implementation:

function Parent(name) {
    this.name = name;
    this.arr = [1]
}
Parent.prototype.say = function () { console.log('hello') }
function Son(name, age) {
    Parent.call(this, name) // Second time this.age = age
}
Parent.prototype = new Son() // once let s1 = new Son('小谭', 18)
let s2 = new Son('Xiaoming', 19)
console.log(s1.say === s2.say) // true
console.log(s1.name, s1.age); //Xiao Tan 18
console.log(s2.name, s2.age); //Xiaoming19
s1.arr.push(2)
console.log(s1.arr, s2.arr); // [ 1, 2 ] [ 1 ] does not share the reference property of the parent class.

advantage:

  • Advantages of retaining the constructor: When creating a subclass instance, you can pass parameters to the parent class constructor.
  • Advantages of retaining the prototype chain: The methods of the parent class are defined on the prototype object of the parent class, which can achieve method reuse.
  • Reference properties of the parent class are not shared. For example, the arr attribute

shortcoming:

  • Since the parent class constructor is called twice, there will be a redundant parent class instance attribute.

Parasitic Combinatorial Inheritance

Core: Combining borrowed constructors to pass parameters and parasitic patterns to achieve inheritance

function Parent(name){
    this.name = name || 'xt',
    this.arr = [1]
}
function Son(name,age){
    Parent.call(this,name) // core
    this.age = age
}
Parent.prototype.say = function() {  
    console.log('hello');
}
Son.prototype = Object.create(Parent.prototype) // The core creates an intermediate object, and the child class prototype and the parent class prototype are isolated.
Son.prototype.constructor = Son
let p1 = new Parent()

let s1 = new Son("Xiaohong",18)
let s2 = new Son("小黑",19)
console.log(p1.constructor); //[Function: Parent]
console.log(s1.constructor); // [Function: Son]
console.log(s1.say() === s2.say()); //true
console.log(s1.name,s1.age); // Xiaohong 18
console.log(s2.name,s2.age); //Little Black 19
s1.arr.push(2)
console.log(s1.arr,s2.arr); // [ 1, 2 ] [ 1, 2 ]

Parasitic composition inheritance can be regarded as the best inheritance of reference type inheritance

Summarize

This is the end of this article about JS inheritance. For more information about JS inheritance, please search for previous articles on 123WORDPRESS.COM or continue to browse the following related articles. I hope you will support 123WORDPRESS.COM in the future!

You may also be interested in:
  • Detailed explanation of Js class construction and inheritance cases
  • An article teaches you JS function inheritance
  • Differences between ES6 inheritance and ES5 inheritance in js
  • A brief talk about JavaScript parasitic composition inheritance
  • JavaScript object-oriented class inheritance case explanation
  • In-depth explanation of the various methods and advantages and disadvantages of JavaScript inheritance

<<:  MYSQL performance analyzer EXPLAIN usage example analysis

>>:  Nexus private server construction principle and tutorial analysis

Recommend

How to capture exceptions gracefully in React

Table of contents Preface ErrorBoundary Beyond Er...

Detailed explanation of the difference between in and exists in MySQL

1. Prepare in Advance For your convenience, I cre...

Summary of basic SQL statements in MySQL database

This article uses examples to describe the basic ...

Docker image import, export, backup and migration operations

Export: docker save -o centos.tar centos:latest #...

Simple understanding and examples of MySQL index pushdown (ICP)

Preface Index Condition Pushdown (ICP) is a new f...

Why can't the MP4 format video embedded in HTML be played?

The following code is in my test.html. The video c...

Vue-pdf implements online preview of PDF files

Preface In most projects, you will encounter onli...

Interviewer asked how to achieve a fixed aspect ratio in CSS

You may not have had any relevant needs for this ...

Detailed explanation of various HTTP return status codes

When a request is sent to your server to display ...

Several common ways to deploy Tomcat projects [tested]

1 / Copy the web project files directly to the we...

Tomcat common exceptions and solution code examples

The company project was developed in Java and the...

Summary of various methods of implementing article dividing line styles with CSS

This article summarizes various ways to implement...

Apache Log4j2 reports a nuclear-level vulnerability and a quick fix

Apache Log4j2 reported a nuclear-level vulnerabil...