一篇文章教会你什么是闭包

原文链接:https://note.noxussj.top/?source=helloworld


什么是闭包?

闭包的概念并不复杂,但是它的定义比较绕(就像平时经常用到它,却又说不出来是什么)。可以在一个作用域中调用函数的内部函数并访问到该函数中的作用域的成员,这就是闭包。给一个建议,网上闭包的概念可以搜出来一大堆,但是你真的了解它吗?你有去调试看过它真的存在吗?一直处于理论状态,没有去真正实践过,这样的知识背下来了也没有太大意义,到面试的时候也表达不清楚。

闭包的原理

函数在执行的时候会放到一个执行栈中,当函数执行完毕之后会从执行栈移除,但是堆上的作用域成员因为被外部引用不能释放,因此内部函数依然可以访问外部函数的成员。

为了更好的理解,我列举以下两个场景,一个是存在闭包,一个是不存在闭包。并且通过浏览器调试工具去查看闭包。

基础案例

场景 1

function makeFn() { let msg = 'Hello function' console.log(msg) } makeFn()

执行过程如下:

  1. 定义 makeFn 函数
  2. 调用 makeFn 函数
  3. 定义 msg 变量
  4. 打印 msg 变量
  5. 销毁 msg 变量
  6. 执行完毕

调试结果

img

从上图中可以看到,当我们准备打印 msg 变量的时候,它是从当前作用域读取出来的。

场景 2

function makeFn() { let msg = 'Hello function' return function inside() { console.log(msg) } } let fn = makeFn() // 执行 makeFn 函数,返回 inside 函数 fn() // 执行 inside 函数

执行过程如下:

  1. 定义 makeFn 函数
  2. 调用 makeFn 函数
  3. 定义 msg 变量
  4. 定义 inside 函数(虽然还没被调用,但是由于该函数访问了外部函数的变量,所以外部函数的执行上文对象不会被销毁,形成闭包)
  5. makeFn 函数执行完毕,并将 inside 函数返回给 fn
  6. 调用 fn 函数
  7. inside 函数访问 msg 变量(从闭包中获取 msg)
  8. 打印 msg 变量
  9. 执行完毕

调试结果

img

从上图中可以看到,当我们准备打印 msg 变量的时候,它是从闭包里面读取出来的。

还有一点,闭包会造成内存泄露,这句话不完全对,何为内存泄露?例如上图的 msg 变量,是我想要访问的变量,它不叫内存泄露。内存泄露是指在闭包中存在一些我不想要的资源,或者是无意间生成出来的。

点赞
收藏

评论区

加载中...

相关推荐

JS核心原理理解闭包

前置概念在正式看闭包之前,我们先来学习一下前置知识,那就是JS中的作用域,我们知道,在ES5之中,作用域分为两种:全局作用域和函数作用域,随着ES6的到来,新增了块级作用域,想更好的理解闭包,那么搞清楚作用域是首要条件全局作用域我们知道,对于变量而言,我们一般会分成两类:全局变量和局部变量,一般定义在最外围环境的为全局变量,定义在函数当中的为局部变量,在we

JS - 从执行上下文的角度来理解闭包

今天看到一篇关于闭包的文章,里面有这样一句话“就我而言对于闭包的理解仅止步于一些概念,看到相关代码知道这是个闭包,但闭包能解决哪些问题场景我了解的并不多”,这说的不就是我么,每每在面试中被问及什么是闭包,大部分情况下得到的答复是(至少我以前是)A函数嵌套B函数,B函数使用了A函数的内部变量,且A函数返回B函数,这就是闭包。而往往面试官想要听到的并不是这样的

你不可不知的JS面试题(第三期)

1、什么是闭包?如图所示,闭包就是一个定义在函数内部的函数,其作用是将函数内部和函数外部连接起来。大家知道,作用域的问题,就是在函数内部定义的变量称为局部变量,外部取不到值。下面我们通过代码来更加详细地看一下:function A()       let x  1;       return function B()           c

Python 中的闭包

闭包定义:如果在一个内部函数里,对在外部作用于(但不是在全局作用域)的变量进行引用,那么内部函数就被认为是闭包Python中的闭包原文出处:田小计划(http://www.cnblogs.com/wilber2013/p/4658894.html)闭包(closure)是函数式编程的重要的语法结构

JS 闭包(内存溢出与内存泄漏)(垃圾回收机制)

1.有关闭包定义闭包是指有权访问另一个函数作用域中变量的函数,创建闭包的最常见的方式就是在一个函数内创建另一个函数,通过另一个函数访问这个函数的局部变量闭包的特性:函数内再嵌套函数内部函数可以引用外层的参数和变量参数和变量不会被垃圾回收机制回收

Swift讲解专题八——闭包

Swift讲解专题八——闭包一、引言      Swift中的闭包是有一定功能的代码块,这十分类似于ObjectiveC中的block语法。Swift中的闭包语法风格十分简洁,其作用和函数的作用相似。二、从一个系统函数看闭包      Swift标准函数库中提供了一个sort排序函数,对