JS function call, apply and bind super detailed method

JS function call, apply and bind super detailed method

JS function call, apply and bind methods

1. call() method

Calling call() method will immediately execute the target function and change the reference of this inside the function. This points to the first parameter of the method, and any parameters listed one by one will be passed in as parameters of the target function one by one.

/* Normal mode */

let obj = {
  sum(a, b) {
    console.log(this)
    return a + b
  }
}

// Execute the apply and bind methods of the sum function. The printed this is the same as below. obj.sum.call() // Print window
obj.sum.call(undefined, 1, 2) // Print window
obj.sum.call(null, 1, 2) // Print window

/* Strict mode */
'use strict'

// Execute the apply and bind methods of the sum function, and print this as below obj.sum.call() // Print undefined
obj.sum.call(undefined, 1, 2) // prints undefined
obj.sum.call(null, 1, 2) // prints null

1. Simulation implementation of call() method

Key points:

  • myCall() method is added to the Function prototype object. When the target function calls this method, this inside the myCall() method will point to the target function.
  • Execute the target function as a method of the context object, so that this inside the target function will point to the context object.
  • Remove the target function from the context object
  • Use the spread operator ... to process the parameters passed into the target function

In the simulation implementation of the call(), apply(), and bind() methods, when the first parameter is not passed or undefined or null is passed, unified processing is done here in JS normal mode and strict mode, that is, this inside the target function points to the window object.

The code is as follows:

Function.prototype.myCall = function (context, ...args) {
  if (context === undefined || context === null) {
    context = window
  }
  // The following line is the core code context.fn = this
  const result = context.fn(...args)
  delete context.fn
  return result
}

let obj1 = {
  basicNum: 1,
  sum(a, b) {
    console.log(this)
    return this.basicNum + a + b
  }
}
let obj2 = {
  basicNum: 9
}
console.log(obj1.sum.call(obj2, 2, 3)) // 14
console.log(obj1.sum.myCall(obj2, 2, 3)) // 14

2. apply() method

Calling apply() method will immediately execute the target function and change the reference of this inside the function. This points to the first parameter of the method. The second parameter is a parameter array or an arguments object . Each parameter represented by each array element or arguments object will be passed in one by one as the parameter of the target function.

1. Simulation implementation of apply() method

Key points:

  • myApply() method is added to the Function prototype object. When the target function calls this method, this inside the myApply() method will point to the target function.
  • Execute the target function as a method of the context object, so that this inside the target function will point to the context object.
  • Remove the target function from the context object
  • Use the spread operator ... to process the parameters passed into the target function

The code is as follows:

Function.prototype.myApply = function (context, args) {
  if (context === undefined || context === null) {
    context = window
  }
  // The following line is the core code context.fn = this
  const result = context.fn(...args)
  delete context.fn
  return result
}

console.log(obj1.sum.apply(obj2, [2, 3])) // 14
console.log(obj1.sum.myApply(obj2, [2, 3])) // 14

3. bind() method

  • Calling bind() method will return a new function - a copy of the target function. this inside the function points to the first parameter of the method, and any parameters listed one by one will be passed in as parameters of the target function one by one. Executing the new function afterwards is equivalent to executing the target function.
  • bind() method implements function currying, so you can pass parameters to the target function twice. The first parameter is listed after the first parameter of the bind() method, and the second parameter is listed in the new function.

1. Simulation implementation of bind() method

Key points:

  • myBind() method is added to the Function prototype object. When the target function calls this method, the this inside the myBind() method will point to the target function.
  • Execute the target function as a method of the context object, so that this inside the target function will point to the context object.
  • Remove the target function from the context object
  • Use the spread operator ... to process the initial and subsequent parameters passed into the target function.

The code is as follows:

Function.prototype.myBind = function (context, ...initArgs) {
  if (context === undefined || context === null) {
    context = window
  }
  // Cache this value const _this = this
  return function (...args) {
    // The following line is the core code context.fn = _this
    const result = context.fn(...initArgs, ...args)
    delete context.fn
    return result
  }
}

console.log(obj1.sum.bind(obj2, 2)(3)) // 14
console.log(obj1.sum.myBind(obj2, 2)(3)) // 14

IV. Conclusion

Similarities and differences between the three methods:

Similarities:
Both can change the internal this point when the target function is executed. The first parameter of the method is used to specify the internal this value when the function is executed. It supports passing any number of parameters to the target function. If no value is passed to the first parameter of the method or undefined or null is passed, then in JavaScript normal mode, this inside the target function points to the window object, and in strict mode, it points to undefined or null respectively.

the difference:
The apply() method accepts two parameters, while the call() and bind() methods accept multiple parameters.
When the apply() method passes parameters to the target function, it only needs to pass the parameter array or arguments object as the second parameter of the method, while the call() and bind() methods need to list the parameters one by one after a parameter of the method.
When the call() and apply() methods are called, the target function is executed immediately, but the bind() method will not. It will return a new function - a copy of the target function. The this inside the function points to the first parameter of the bind() method. Executing the new function afterwards is equivalent to executing the target function.
Only the bind() method implements function currying, so it can pass parameters to the target function twice.

The above is the details of the super detailed methods of call, apply and bind of JS functions. For more information about the call, apply and bind methods of JS functions, please pay attention to other related articles on 123WORDPRESS.COM!

You may also be interested in:
  • JavaScript functional programming basics
  • An article teaches you JS function inheritance
  • JavaScript Basics Series: Functions and Methods
  • JavaScript function call, apply and bind method case study
  • Detailed explanation of the difference between arrow functions and normal functions in JavaScript
  • JavaScript knowledge: Constructors are also functions
  • Use of JavaScript sleep function
  • Detailed examples of variable and function promotion in JavaScript
  • Summary of 50+ Utility Functions in JavaScript
  • 15 JavaScript functions worth collecting

<<:  Solve the problem that the commonly used Linux command "ll" is invalid or the command is not found

>>:  MySQL slow query method and example

Recommend

MySQL aggregate function sorting

Table of contents MySQL result sorting - Aggregat...

HTML set as homepage and add to favorites_Powernode Java Academy

How to implement the "Set as homepage" ...

Detailed explanation of Vue monitoring attribute graphic example

Table of contents What is the listener property? ...

MySQL 5.7.23 installation and configuration graphic tutorial

This article records the detailed installation pr...

Explanation of Truncate Table usage

TRUNCATE TABLE Deletes all rows in a table withou...

Solution to Chinese garbled characters when operating MySQL database in CMD

I searched on Baidu. . Some people say to use the...

Several ways to add timestamps in MySQL tables

Scenario: The data in a table needs to be synchro...

Tutorial on installing MySQL 8.0.11 using RPM on Linux (CentOS7)

Table of contents 1. Installation preparation 1. ...

Summary of knowledge points on using calculated properties in Vue

Computed properties Sometimes we put too much log...

Detailed deployment of Alibaba Cloud Server (graphic tutorial)

I have recently learned web development front-end...

Analysis of examples of using anti-shake and throttling in Vue components

Be careful when listening for events that are tri...

HTML version declaration DOCTYPE tag

When we open the source code of a regular website...

Vue integrates Tencent Map to implement API (with DEMO)

Table of contents Writing Background Project Desc...

MySQL merges multiple rows of data based on the group_concat() function

A very useful function group_concat(), the manual...

How to modify the root password of mysql in docker

The first step is to create a mysql container doc...