位置: 编程技术 - 正文

深入理解JavaScript 闭包究竟是什么(深入理解中国式现代化)

编辑:rootadmin

1.简单的例子

首先从一个经典错误谈起,页面上有若干个div, 我们想给它们绑定一个onclick方法,于是有了下面的代码很简单的功能可是却偏偏出错了,每次alert出的值都是4,简单的修改就好使了

2.内部函数

让我们从一些基础的知识谈起,首先了解一下内部函数。内部函数就是定义在另一个函数中的函数。例如:innerFn就是一个被包在outerFn作用域中的内部函数。这意味着,在outerFn内部调用innerFn是有效的,而在outerFn外部调用innerFn则是无效的。下面代码会导致一个JavaScript错误:

不过在outerFn内部调用innerFn,则可以成功运行:

2.1伟大的逃脱

JavaScript允许开发人员像传递任何类型的数据一样传递函数,也就是说,JavaScript中的内部函数能够逃脱定义他们的外部函数。

逃脱的方式有很多种,例如可以将内部函数指定给一个全局变量:调用outerFn时会修改全局变量globalVar,这时候它的引用变为innerFn,此后调用globalVar和调用innerFn一样。这时在outerFn外部直接调用innerFn仍然会导致错误,这是因为内部函数虽然通过把引用保存在全局变量中实现了逃脱,但这个函数的名字依然只存在于outerFn的作用域中。

也可以通过在父函数的返回值来获得内部函数引用

这里并没有在outerFn内部修改全局变量,而是从outerFn中返回了一个对innerFn的引用。通过调用outerFn能够获得这个引用,而且这个引用可以可以保存在变量中。

这种即使离开函数作用域的情况下仍然能够通过引用调用内部函数的事实,意味着只要存在调用内部函数的可能,JavaScript就需要保留被引用的函数。而且JavaScript运行时需要跟踪引用这个内部函数的所有变量,直到最后一个变量废弃,JavaScript的垃圾收集器才能释放相应的内存空间(红色部分是理解闭包的关键)。

说了半天总算和闭包有关系了,闭包是指有权限访问另一个函数作用域的变量的函数,创建闭包的常见方式就是在一个函数内部创建另一个函数,就是我们上面说的内部函数,所以刚才说的不是废话,也是闭包相关的 ^_^

1.2变量的作用域

内部函数也可以有自己的变量,这些变量都被限制在内部函数的作用域中:每当通过引用或其它方式调用这个内部函数时,就会创建一个新的innerVar变量,然后加1,最后显示

内部函数也可以像其他函数一样引用全局变量:

现在每次调用内部函数都会持续地递增这个全局变量的值:

但是如果这个变量是父函数的局部变量又会怎样呢?因为内部函数会引用到父函数的作用域(有兴趣可以了解一下作用域链和活动对象的知识),内部函数也可以引用到这些变量

这一次结果非常有意思,也许或出乎我们的意料

我们看到的是前面两种情况合成的效果,通过每个引用调用innerFn都会独立的递增outerVar。也就是说第二次调用outerFn没有继续沿用outerVar的值,而是在第二次函数调用的作用域创建并绑定了一个一个新的outerVar实例,两个计数器完全无关。

当内部函数在定义它的作用域的外部被引用时,就创建了该内部函数的一个闭包。这种情况下我们称既不是内部函数局部变量,也不是其参数的变量为自由变量,称外部函数的调用环境为封闭闭包的环境。从本质上讲,如果内部函数引用了位于外部函数中的变量,相当于授权该变量能够被延迟使用。因此,当外部函数调用完成后,这些变量的内存不会被释放(最后的值会保存),闭包仍然需要使用它们。

3.闭包之间的交互

当存在多个内部函数时,很可能出现意料之外的闭包。我们定义一个递增函数,这个函数的增量为2

我们映射返回两个内部函数的引用,可以通过返回的引用调用任一个内部函数,结果:

innerFn1和innerFn2引用了同一个局部变量,因此他们共享一个封闭环境。当innerFn1为outerVar递增一时,久违innerFn2设置了outerVar的新的起点值,反之亦然。我们也看到对outerFn的后续调用还会创建这些闭包的新实例,同时也会创建新的封闭环境,本质上是创建了一个新对象,自由变量就是这个对象的实例变量,而闭包就是这个对象的实例方法,而且这些变量也是私有的,因为不能在封装它们的作用域外部直接引用这些变量,从而确保了了面向对象数据的专有性。

4.解惑

现在我们可以回头看看开头写的例子就很容易明白为什么第一种写法每次都会alert 4了。上面代码在页面加载后就会执行,当i的值为4的时候,判断条件不成立,for循环执行完毕,但是因为每个span的onclick方法这时候为内部函数,所以i被闭包引用,内存不能被销毁,i的值会一直保持4,直到程序改变它或者所有的onclick函数销毁(主动把函数赋为null或者页面卸载)时才会被回收。这样每次我们点击span的时候,onclick函数会查找i的值(作用域链是引用方式),一查等于4,然后就alert给我们了。而第二种方式是使用了一个立即执行的函数又创建了一层闭包,函数声明放在括号内就变成了表达式,后面再加上括号括号就是调用了,这时候把i当参数传入,函数立即执行,num保存每次i的值。

这一通下来想必大家也和我一样,对闭包有所了解了吧,当然完全了解的话需要把函数的执行环境和作用域链搞清楚 ^_^

推荐整理分享深入理解JavaScript 闭包究竟是什么(深入理解中国式现代化),希望有所帮助,仅作参考,欢迎阅读内容。

深入理解JavaScript 闭包究竟是什么(深入理解中国式现代化)

文章相关热门搜索词:深入理解ffmpeg pdf,深入理解计算机系统,深入理解新发展理念,深入理解计算机系统,深入理解javascript,深入理解javascript特性.pdf,深入理解javascript特性.pdf,深入理解javascript,内容如对您有帮助,希望把文章链接给更多的朋友!

用JavaScript获取DOM元素位置和尺寸大小的方法 在一些复杂的页面中经常会用JavaScript处理一些DOM元素的动态效果,这种时候我们经常会用到一些元素位置和尺寸的计算,浏览器兼容性问题也是不可忽

基于JavaScript实现 获取鼠标点击位置坐标的方法 在一些DOM操作中我们经常会跟元素的位置打交道,鼠标交互式一个经常用到的方面,令人失望的是不同的浏览器下会有不同的结果甚至是有的浏览器下

有关javascript的性能优化 (repaint和reflow) repaint(重绘),repaint发生更改时,元素的外观被改变,且在没有改变布局的情况下发生,如改变outline,visibility,backgroundcolor,不会影响到dom结构渲染。reflow

标签: 深入理解中国式现代化

本文链接地址:https://www.jiuchutong.com/biancheng/377665.html 转载请保留说明!

上一篇:关于JavaScript中string 的replace(关于javascript中数组的说法不正确)

下一篇:用JavaScript获取DOM元素位置和尺寸大小的方法(js获取tbody)

  • 小规模纳税人要交增值税吗
  • 应交所得税的计税依据
  • 印花税是什么时候交的钱
  • 新企业会计准则2021
  • 合同资产和合同负债属于什么科目
  • 个体户查账征收怎么交税?
  • 专项应付款和政府补助的区别是什么
  • 供热管道属于什么经营范围内
  • 其他货币资金存出投资款什么时候用
  • 递延收益是什么科目应该怎么处理
  • 用库存物资抵货怎么做账
  • 最新工程施工会计处理流程
  • 企业自建房转让如何交土地增值税
  • 企业销售货物后,若发生销货退回或销售折让
  • 冷库租赁收入税率
  • 税控盘抵扣政策依据
  • 税率是3%开成5%怎么办
  • 自然人代人开普票合法吗
  • 销售开发后的产品
  • 福利费用属于什么费用
  • 资产处置损失计算方法
  • 企业生产经营模式
  • 外账不能出现收据
  • 光纤熔接发票属什么类别
  • 2019年以后转登记为小规模纳税人有无时间要求?
  • 以前年度资产损失,汇算清缴怎么填表
  • 物流公司油卡怎么抵税的
  • 一般纳税人进项税额转出会计分录
  • 给对方发短信显示imessage
  • 医药批发行业增值税税负率
  • 公司收到政府科技创新奖
  • 跨年度冲减收入
  • 委托加工代收代缴增值税吗
  • u盘win10系统安装教程
  • 固定资产更新改造支出资本化
  • 购入工程物资用于建设厂房,购入后直接领用至工程项目
  • 营业外收入增加说明什么问题
  • 装修费怎么记会计科目
  • 银行罚息可不可以扣除
  • 企业银行贷款利率2023
  • 头歌java入门运算符和表达式答案
  • 债务重组亏损计入
  • php生成随机6位数
  • uniapp 开发安卓app怎么打包迭代版本
  • webstorm功能
  • mobilenet模型
  • 宝塔wordpress安装
  • 工会经费的来源包括
  • 采购国产设备退税公告
  • 应付债券和应付利息
  • 委托贷款利息收入
  • php.ini上传限制
  • 债务抵销的顺序
  • 自产用于捐赠的会计处理
  • 土地承包经营权上的房屋
  • 个体工商户怎么变更法人
  • 我是小规模纳税人,客户都想获得13%的专票
  • 票已收到、款未付会计分录
  • 免抵退的定义
  • 新企业如何建帐
  • 多个客户账款明细
  • win10 预览版变正式版
  • 怎么才能更好的优化我的电脑
  • win8应用程序
  • win7不重装修复系统
  • winbox app
  • textview可以点击吗
  • a*算法的优缺点
  • 关于全局变量和局部变量说法不正确的是
  • 安卓系统引导程序
  • listview添加数据
  • jQuery 获取跨域XML(RSS)数据的相关总结分析
  • 进项票当月认证怎么操作
  • 销售货物免征增值税时收取的增值税税款需计入当期损益
  • 山西国家税务总局
  • 云南省残疾人就业服务中心官网
  • 创新税务稽查方案
  • 自建房交契税需要什么
  • 2020年南通居民医保缴费标准
  • 土地要钻几回才能挖
  • 免责声明:网站部分图片文字素材来源于网络,如有侵权,请及时告知,我们会第一时间删除,谢谢! 邮箱:opceo@qq.com

    鄂ICP备2023003026号

    网站地图: 企业信息 工商信息 财税知识 网络常识 编程技术

    友情链接: 武汉网站建设