JS闭包用法实例分析


Posted in Javascript onMarch 27, 2017

本文实例讲述了JS闭包用法。分享给大家供大家参考,具体如下:

<!DOCTYPE html>
<html>
  <head>
    <meta charset="UTF-8">
    <title></title>
  </head>
  <body>
    <script type="text/javascript">
//      第一,函数作为返回值
      function fn(){
        var max = 10;
        return function bar(x){
          if(x > max) {
            console.log(x);
          }
        };
      }
      var f1 = fn();
      f1(15);
    </script>
    <script type="text/javascript">
//      第二,函数作为参数被传递
      var max = 10;
      fn = function(x){
        if(x > max){
          console.log(x);//15
        }
      };
      (function(f){
        var max = 100;
        f(15);
      })(fn);
    </script>
    <script>
      function fn(){
        var max = 10;
        return function bar(x){
          if(if > max){
            console.log(x);
          }
        };
      }
      var f1 = fn();
        max = 100;
      f1(15);
    </script>
  </body>
</html>

第一步,代码执行前生成全局上下文环境,并在执行时对其中的变量进行赋值。此时全局上下文环境是活动状态。

全局上下文环境:max是undefined

第二步,执行var f1 = fn();代码时,调用fn(),产生fn()执行上下文环境,压栈,并设置为活动状态。

fn()上下文环境:max是10

第三步,执行完var f1 = fn();,fn()调用完成。按理说应该销毁掉fn()的执行上下文环境,但是这里不能这么做。

注意,重点来了:因为执行fn()时,返回的是一个函数。函数的特别之处在于可以创建一个独立的作用域。

而正巧合的是,返回的这个函数体中,还有一个自由变量max要引用fn作用域下的fn()上下文环境中的max。

因此,这个max不能被销毁,销毁了之后bar函数中的max就找不到值了。因此,这里的fn()上下文环境不能被销毁,还依然存在与执行上下文栈中。

执行到max = 100;时,全局上下文环境将变为活动状态,但是fn()上下文环境依然会在执行上下文栈中。

另外,执行完max = 100;,全局上下文环境中的max被赋值为100。

全局上下文环境:max是100 fn()上下文环境:max是10

第四步,执行到f1(15);,执行f1(15),即执行bar(15),创建bar(15)上下文环境,并将其设置为活动状态。

执行bar(15)时,max是自由变量,需要向创建bar函数的作用域中查找,找到了max的值为10。

这里的重点就在于,创建bar函数是在执行fn()时创建的。fn()早就执行结束了,但是fn()执行上下文环境还存在与栈中,因此bar(15)时,max可以查找到。如果fn()上下文环境销毁了,那么max就找不到了。

使用闭包会增加内容开销,现在很明显了吧!

第五步,执行完f1(15);就是上下文环境的销毁过程,这里就不再赘述了。

闭包和作用域、上下文环境有着密不可分的关系,真的是“想说爱你不容易”!

另外,闭包在jQuery中的应用非常多,无论你是想了解一个经典的框架/类库,还是想自己开发一个插件或者类库,像闭包、原型这些基本的理论,是一定要知道的。否则,到时候出了BUG你都不知道为什么,因为这些BUG可能完全在你的知识范围之外。

更多关于JavaScript相关内容可查看本站专题:《javascript面向对象入门教程》、《JavaScript中json操作技巧总结》、《JavaScript切换特效与技巧总结》、《JavaScript查找算法技巧总结》、《JavaScript错误与调试技巧总结》、《JavaScript数据结构与算法技巧总结》、《JavaScript遍历算法与技巧总结》及《JavaScript数学运算用法总结》

希望本文所述对大家JavaScript程序设计有所帮助。

Javascript 相关文章推荐
JQuery触发事件例如click
Sep 11 Javascript
jquery果冻抖动效果实现方法
Jan 15 Javascript
JavaScript 事件绑定及深入
Apr 13 Javascript
教你使用javascript简单写一个页面模板引擎
May 05 Javascript
AngularJS基础学习笔记之指令
May 10 Javascript
关于Javascript回调函数的一个妙用
Aug 29 Javascript
谈谈jQuery之Deferred源码剖析
Dec 19 Javascript
js实现时间轴自动排列效果
Mar 09 Javascript
jQuery操作之效果详解
May 19 jQuery
vue过滤器用法实例分析
Mar 15 Javascript
Vue+Typescript中在Vue上挂载axios使用时报错问题
Aug 07 Javascript
JS XMLHttpRequest原理与使用方法深入详解
Apr 30 Javascript
vue 2.0组件与v-model详解
Mar 27 #Javascript
JavaScript无缝滚动效果的实例代码
Mar 27 #Javascript
JS数组搜索之折半搜索实现方法分析
Mar 27 #Javascript
javascript实现下雨效果
Mar 27 #Javascript
HTML的select控件美化
Mar 27 #Javascript
JS实现的点击表头排序功能示例
Mar 27 #Javascript
深入理解AngularJS中的ng-bind-html指令
Mar 27 #Javascript
You might like
PHP动态柱状图实现方法
2015/03/30 PHP
Zend Framework教程之Loader以及PluginLoader用法详解
2016/03/09 PHP
javascript 获取url参数和script标签中获取url参数函数代码
2010/01/22 Javascript
Javascript 通过json自动生成Dom的代码
2010/04/01 Javascript
jQuery中对未来的元素绑定事件用bind、live or on
2014/04/17 Javascript
jQuery中outerWidth()方法用法实例
2015/01/19 Javascript
javascript操作表格排序实例分析
2015/05/06 Javascript
JS实现转动随机数抽奖特效代码
2020/04/16 Javascript
JavaScript中apply方法的应用技巧小结
2016/09/29 Javascript
微信小程序 选择器(时间,日期,地区)实例详解
2016/11/16 Javascript
微信小程序 常见问题总结(4058,40013)及解决办法
2017/01/11 Javascript
利用vscode编写vue的简单配置详解
2017/06/17 Javascript
原生JavaScript实现todolist功能
2018/03/02 Javascript
详解Typescript 内置的模块导入兼容方式
2020/05/31 Javascript
详解JavaScript执行模型
2020/11/16 Javascript
Python的Flask框架中实现分页功能的教程
2015/04/20 Python
简单谈谈python中的lambda表达式
2018/01/19 Python
Python打印“菱形”星号代码方法
2018/02/05 Python
解决Pytorch 训练与测试时爆显存(out of memory)的问题
2019/08/20 Python
python函数局部变量、全局变量、递归知识点总结
2019/11/15 Python
python GUI库图形界面开发之PyQt5表格控件QTableView详细使用方法与实例
2020/03/01 Python
python 在threading中如何处理主进程和子线程的关系
2020/04/25 Python
python利用google翻译方法实例(翻译字幕文件)
2020/09/21 Python
巧用CSS3 border实现图片遮罩效果代码
2012/04/09 HTML / CSS
HTML5 新事件 小结
2009/07/16 HTML / CSS
N.Peal官网:来自伦敦的高档羊绒品牌
2018/10/29 全球购物
台湾租车首选品牌:IWS艾维士租车
2019/05/03 全球购物
寄语学生的话
2014/04/10 职场文书
小学六年级学生评语
2014/04/22 职场文书
《田忌赛马》教学反思
2016/02/19 职场文书
Oracle更换为MySQL遇到的问题及解决
2021/05/21 Oracle
Jupyter Notebook 如何修改字体和大小以及更改字体样式
2021/06/03 Python
SQL实现LeetCode(197.上升温度)
2021/08/07 MySQL
SQL Server远程连接的设置步骤(图文)
2022/03/23 SQL Server
PostgreSQL 插入INSERT、删除DELETE、更新UPDATE、事务transaction
2022/04/12 PostgreSQL
python如何为list实现find方法
2022/05/30 Python