# 闭包作用域

闭包即是一种机制

定义:它是函数运行时候所产生的的机制,函数执行会形成一个全新的私有上下文,可以保护里面的私有变量和外界互不干扰(保护机制)
大家认为:需要当前上下文不能被出栈释放,这样的私有变量及它的值也不会被释放掉(保存机制)

面试:函数执行形成一个私有的上下文,如果当前上下文的私有变量,有被外界所占用,那么当前私有上下文就不能出栈释放,自然而然里面的私有变量被保存保护起来了,不被外界干扰,操作里面的变量不会影响外界,这种机制叫闭包

作用:保存和保护

经典例题1

let x = 1; 
function A(y){
  let x = 2; 
  function B(z){
    console.log(x+y+z);
  }
  return B; 
}
let C = A(2); 
C(3); 

解题思路

经典例题2

let x = 5; 
function fn(x) {
  return function(y) {
    console.log(y + (++x));
  }

}
let f = fn(6); 
f(7); 
fn(8)(9); 
f(10); 
console. log(x); 

++i / i++

let i = 10;

i++:sum = 5+(i++); 先计算,再累加 (sum = 5+10; i = 11)
++i:sum = 5+(++i); 先累加,再计算 (sum = 5+11; i = 11)

解题思路

经典例题3

let a=0,
    b=0;
function A(a){
  A=function(b){
      alert(a+b++);
  };
  alert(a++);
}
A(1);
A(2);

解题思路

# 内存优化

栈内存(执行上下文)

一般情况下,函数执行完,所形成的上下文会被出栈释放掉。
特殊情况:当前上下文中某些内容被上下文以外的食物占用了,此时不能出栈释放
全局上下文:加载页面创建的,也是只有页面关闭才会被释放掉。

堆内存的垃圾回收机制

1、引用计数(IE为主):在某些情况下会导致计数混乱,这样会造成内存不能被释放(内存泄漏)
2、检测引用(占用)/标记清除(谷歌为主):浏览器在空闲时候会依次检测所有的堆内存,把没有被任何事物占用的内存释放掉,以此来优化内存。

手动释放内存,其实就是解除占用(手动赋值为null即可)

# 闭包好不好?

大量应用闭包肯定会导致内存的泄漏,但是闭包保护和保存作用,在真实开发中我们还是需要的,所以需要学会“合理使用闭包”

# 闭包的应用:

ECStack/EC/AO/VO/SCOPE/SCOPE-CHAIN/

1、实战用途
2、高阶变成:柯理化/惰性函数/componse函数/释放不释放/垃圾回收机制
3、源码分析:JQ/Lodash/React(Redux/高阶组件/Hooks)...
4、自己封装插件组件的时候