2026/6/20 10:00:08
网站建设
项目流程
网站宣传流程,长治房产网站建设,服务器分配网络提高网站访问速度,沭阳做网站公司排名前十让人迷惑的闭包
闭包是 JavaScript 中一个非常容易让人迷惑的知识点对于那些有一点 JavaScript 使用经验但从未真正理解闭包概念的人来说#xff0c;理解闭包可以看作是某种意义上的重生#xff0c;但是需要付出非常多的努力和牺牲才能理解这个概念。回忆我前几年的时光…让人迷惑的闭包闭包是 JavaScript 中一个非常容易让人迷惑的知识点对于那些有一点 JavaScript 使用经验但从未真正理解闭包概念的人来说理解闭包可以看作是某种意义上的重生但是需要付出非常多的努力和牺牲才能理解这个概念。回忆我前几年的时光大量使用 JavaScript 但却完全不理解闭包是什么总感觉这门语言有其隐蔽的一面如果能够掌握将会功力大涨但讽刺的是我始终无法掌握其中的门道还记得我曾经大量阅读早期框架的源码试图能够理解闭包的工作原理现在还能回忆起我的脑海中第一次浮现出关于“模块模式”相关概念时的激动心情。闭包确实是 JavaScript 中一个很难理解的知识点接下来我们就对其一步步来进行剖析看看它到底有什么神奇之处。JS 中函数是一等公民在 JavaScript 中函数是非常重要的并且是一等公民意味着函数的使用是非常的灵活的函数可以作为另外一个函数的参数也可以作为另外一个函数的返回值来使用将函数作为另外一个函数的参数functionfoo(a){a()}functionbar(){console.log(bar)}foo(bar)functioncalc(num1,num2,calcFn){console.log(calcFn(num1,num2))}functionadd(num1,num2){returnnum1num2}functionsub(num1,num2){returnnum1-num2}functionmul(num1,num2){returnnum1*num2}varm30varn20calc(m,n,add)calc(m,n,sub)calc(m,n,mul)函数作为返回值的使用// js 语法允许函数内部再定义函数functionfoo(){functionbar(){console.log(bar)}returnbar}varfnfoo()fn()functionmakeAdder(count){functionadd(num){returncountnum}returnadd}varadd5makeAdder(5)add5(6)varadd10makeAdder(10)varadd100makeAdder(100)高阶函数一个函数如果接收另外一个函数作为参数或者该函数会返回另外一个函数作为返回值那么这个函数就称之为是一个高阶函数。数组中的函数使用// 把数组里面的偶数都挑出来varnums[10,5,11,100,55]varnewNums[]for(vari0;inums.length;i){varnumnums[i]if(num%20){newNums.push(num)}}console.log(newNums)// 函数 function独立的 function我们称之为是一个函数// 方法 method当我们的一个函数属于某一个对象时我们称这个函数是这个对象的方法// 数组中的高阶函数// 1、filter过滤varnewNums2nums.filter(function(item){returnitem%20})// 2、map映射varnewNums3nums.map(function(item){returnitem*10})///3、forEach迭代nums.map(function(item){console.log(item)})// 4、find/findIndex查找varitemnums.find(function(item){returnitem11})// 5、reduce累加nums.reduce((previousValue,currentValue,currentIndex,array){returnpreviousValuecurrentValue},0)JS 中闭包的定义闭包的概念出现于 60 年代最早实现闭包的程序是 Scheme那么我们就可以理解为什么 JavaScript 中有闭包因为 JavaScript 中大量的设计是来源于 Scheme 的在计算机科学中对闭包的定义维基百科闭包Closure又称为词法闭包Lexical Closure或函数闭包function closures是在支持头等函数的编程语言中实现词法绑定的一种技术闭包在实现上是一个结构体它存储了一个函数和一个关联的环境相当于一个符号查找表闭包跟函数最大的区别在于当捕捉闭包的时候它的自由变量会在捕捉时被确定这样即使脱离了捕捉时的上下文它也能照常运行MDN 对 JavaScript 闭包的解释一个函数和对其周围状态lexical environment词法环境的引用捆绑在一起或者说函数被引用包围这样的组合就是闭包closure也就是说闭包让你可以在一个内层函数中访问到外层函数的作用域在 JavaScript 中每当创建一个函数闭包就会在函数创建的同时被创建出来老师的总结和理解一个普通的函数如果它可以访问外层作用域的自由变量那么这个函数就是一个闭包从广义的角度来说JavaScript 中的函数都是闭包从狭义的角度来说JavaScript 中一个函数如果访问了外层作用域的变量那么它是一个闭包个人拓展自由变量Free Variable 是指在函数中使用但既不是函数参数也不是在函数内部声明的变量。变量分类:绑定变量Bound Variable函数参数函数内声明的变量let、const、var自由变量Free Variable来自外层作用域的变量来自全局作用域的变量functionfoo(){varnamefoofunctionbar(){console.log(bar,name)}returnbar}varfnfoo()fn()闭包的内存的泄漏闭包会造成内存泄漏其实就是引用链中的所有对象无法释放。只要将下面的 fn 设置为 null在 GC 的下一次检测中它们就会被销毁掉functionfoo(){varnamefoovarage18functionbar(){console.log(name)console.log(age)}returnbar}varfnfoo()fn()// 解决内存泄漏fnnull// 让 fn 指向一个 0x0 的地址