js闭包之相关概念

— 本文是在b站学习所得。

闭包

函数执行,形成的私有作用域,私有栈内存,私有的执行上下文,保护了里面的变量和外界没有必然联系,这种保护机制叫做闭包,市面上的定义为:函数执行形成的不会被销毁私有栈内存。

闭包作用域

  • 创建函数
    • 开辟一个堆内存
    • 把函数体中的代码当做字符串存储进去
    • 把堆内存中的地址赋值给函数名/变量名
    • 函数在哪创建,那么它执行时候所需要查找的上级作用域就是谁
  • 函数执行
    • 形成一个全新的私有作用域、执行上下文、私有栈内存(执行一次形成一个,多个之间也不会产生影响)
    • 形参赋值,变量提升
    • 代码执行(把所属堆内存中的代码字符串拿出来一行行执行)
    • 遇到一个变量,首先看它是否为私有变量(形参和在私有作用域中声明的变量是私有变量),是私有的就操作自己的变量即可,不是私有的则向上级查找,一直找到全局作用域为止 => 作用域链查找机制
    • 私有变量和外界的变量没有必然关系,可以理解为被私有栈内存保护起来了,这种机制其实就是“闭包的保护机制

变量提升

当作用域产生之后,当栈内存形成之后,在代码执行之前,总要进行一步–变量提升,把所有带var和function关键字的提前进行声明或者定义。

全局变量

在全局作用域下形成的变量

私有变量

在私有作用域下,形参和在私有作用域中声明的变量。而函数执行必然形成私有作用域

堆栈内存释放问题

函数执行就会形成栈内存(从内存中分配一块空间),如果内存不销毁释放,就会导致栈内存溢出,电脑卡死

1、堆内存释放

 //创建一个引用类型的值,就会产生一个堆内存,如果当前的堆内存不被其他东西所占用(浏览器会在空闲的时候查找每一个内存的使用情况,不被占用的都会被回收释放掉),则会被释放。
 let obj1 = {
 	name: 'hello'
 };	//创建一块堆内存,并将堆内存地址返回给变量
 let obj2 = obj1;
 //此时obj1和 obj2 都占用着一块堆内存空间,想要释放堆内存,需要手动删除对堆内存的使用(变量和值之间的关系)
 obj1 = null;
 obj2 = null;	//使用空对象指针 null 来解除

2、栈内存释放

 //打开浏览器形成的全局作用域是栈内存
 //手动执行函数形成的私有作用域是栈内存
 //基于es6中的let和const形成的块级作用域也是栈内存
 /*
 * 全局栈内存:只有关掉页面时,才会销毁
 * 私有栈内存:
 * 	1、一般情况下,函数执行完成,形成的私有栈内存就会被销毁掉(排除死递归出现的死循环的模式)
 *  2、但是一旦栈内存中的某个东西(一般是堆地址)被私有作用域以外的事物占用了,则当前私有栈内存不能被立即释放销毁(特点:私有作用域中的私有变量等信息也保存下来) =>市面上认为的闭包:函数执行形成不能被释放的私有栈内存叫做闭包
 */
 function fn1(){
	// ....
 }
 fn1(); //函数执行形成栈内存,执行完成栈内存销毁
 
 function fn2(){
  return function(){
  	// ...
  }
 }
 let f = fn2(); //f占用了fn2执行形成的栈内存中的一个东西(返回小函数对应的堆),则fn2执行形成的栈内存不能被释放了。

两大作用:保护和保存

从性能的角度讲,真实项目中应该减少对闭包的使用,(因为闭包会产生不释放的栈内存,过多使用容易导致内存溢出或者性能降低)
  • 保护:(私有变量和外界没有必然联系)
  • 保存:(形成不销毁的栈内存,里面的私有变量等信息保存下来了)
    1、jquery:前端非常经典的类库:提供了大量的方法供开发人员使用
    =>为了防止全局变量污染(解释:导入jquery之后,他里面有大量的方法,如果这些方法不保护起来,用户编写的方法很容易和jq的方法名字相同产生冲突,冲突可以理解为全局变量污染),jq中的方法和变量需要用闭包保护起来
    2、jquery源码使用闭包的形式使得内部方法名与变量名与外部不冲突。同时通过给全局对象增加属性:jQuery和$,把私有的jQuery方法暴露到全局作用域下,供外面使用(等价于return jQuery)(外界要使用函数中的私有内容,我们可以基于window.xxx 和 return xxx的方式<=传统开发),
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值