What are closures and how to use them?

1. Concept

Closures are functions that can read variables inside other functions. For example, in javascript, only sub-functions inside the function can read local variables, so closures can be understood as "A function defined inside a function". In essence, a closure is a bridge that connects the inside of the function with the outside of the function.

Two, characteristics

  1. function nested function

  2. Parameters and variables outside the function can be referenced inside the function

  3. Parameters and variables are not garbage collected

3. Usage

1. Function as return value

function closure(num) {
    
    
  var count = num
  // t()使用
  // return function getCount() {
    
    
  //   return count++
  // }
  return {
    
    
    plus: function() {
    
    
      return count++
    },
    minus: function() {
    
    
      return count--
    },
    getCount: function() {
    
    
      return count
    }
  }
}
var t = closure(0)
console.log('初始值:' + t.getCount())
t.plus()
console.log('plus后:' + t.getCount())
t.minus()
console.log('minus后:' + t.getCount())

insert image description here

(1) Classic example - timer and closure

1.1 Realize sequential input of 0 1 2 3 4
for (var i = 0; i < 5; i++) {
    
    
  // var则输出5个5,改成let按顺序输出0-4
  setTimeout(() => {
    
    
    console.log(Date.now() + ' ' + i)
  }, 100)
}

insert image description here

1.2 Introduce a closure to save the variable j, put setTimeout into the immediate execution function, pass the loop value j in the for loop as a parameter, and print out 0 1 2 3 4 at the same time after 100 milliseconds
for (var j = 0; j < 5; j++) {
    
    
  (function(j) {
    
    
    setTimeout(() => {
    
    
      console.log(Date.now() + ' ' + j)
    }, 100)
  })(j)
}

insert image description here

1.3 So if we want to output numbers sequentially every 100 milliseconds, how should we change it?
for (var k = 0; k < 5; k++) {
    
    
  (function(k) {
    
    
    setTimeout(function() {
    
    
      console.log(Date.now() + ' ' + k)
    }, 100 * k)
  })(k)
}

insert image description here

k*100 is to set different times for the four timers and start them at the same time, but the execution time is different. The interval of each timer is 100 milliseconds, which realizes the effect of printing every 100 milliseconds.

2. Closures are passed as parameters

 // 第一种写法
 function fun2() {
    
    
   var num = 24
   console.log(++num)
 }
 function fun1(fun) {
    
    
   fun()
 }
 fun1(fun2)
 // 输出结果
 // 25

 // 第二种写法(匿名函数回调)
 void (function(fun) {
    
    
   fun()
 })(fun2)
 // 输出结果
 // 25

Summarize:

advantage:
  1. Can access local variables inside the function
  2. Can avoid global variable pollution
  3. The values ​​of these variables are always kept in memory and will not be automatically cleared after the outer function is called.
shortcoming:
  1. It will increase memory usage, and abuse of closures will affect performance and lead to problems such as memory leaks.
Note: Before exiting the function, delete all unused local variables, and assign the variables to null.

Guess you like

Origin blog.csdn.net/qq_45616003/article/details/124967412