理解javascript闭包


Posted in Javascript onDecember 15, 2015

什么是javascript闭包?
javascript允许使用内部函数,内部函数可以访问它们所在的外部函数中声明的所有局部变量、参数和声明的其他内部函数。当其中一个这样的内部函数在包含它们的外部函数之外被调用时,就会形成闭包。
简单的javascript闭包例子:

<script>
  function f1(){

var n=999;


nAdd=function(){n+=1}


function f2(){



alert(n);


}


return f2;

}

var result=f1();

result(); // 999

nAdd();

result(); // 1000
</script>

在这段代码中,result实际上就是闭包f2函数。它一共运行了两次,第一次的值是999,第二次的值是1000。这证明了,函数f1中的局部变量n一直保存在内存中,并没有在f1调用后被自动清除。
为什么会这样呢?原因就在于f1是f2的父函数,而f2被赋给了一个全局变量,这导致f2始终在内存中,而f2的存在依赖于f1,因此f1也始终在内存中,不会在调用结束后,被垃圾回收机制(garbage collection)回收。
这段代码中另一个值得注意的地方,就是"nAdd=function(){n+=1}"这一行,首先在nAdd前面没有使用var关键字,因此nAdd是一个全局变量,而不是局部变量。其次,nAdd的值是一个匿名函数(anonymous function),而这个匿名函数本身也是一个闭包,所以nAdd相当于是一个setter,可以在函数外部对函数内部的局部变量进行操作。
 闭包的应用:

var singleton = function () {
  var privateVariable;
  function privateFunction(x) {
    ...privateVariable...
  }
 
  return {
    firstMethod: function (a, b) {
      ...privateVariable...
    },
    secondMethod: function (c) {
      ...privateFunction()...
    }
  };
}();

 这个单件通过闭包来实现。通过闭包完成了私有的成员和方法的封装。匿名主函数返回一个对象。对象包含了两个方法,方法1可以方法私有变量,方法2访问内部私有函数。需要注意的地方是匿名主函数结束的地方的'()',如果没有这个'()'就不能产生单件。因为匿名函数只能返回了唯一的对象,而且不能被其他地方调用。这个就是利用闭包产生单件的方法。

闭包的优势:
(1)不增加额外的全局变量,
(2)执行过程中所有变量都是在匿名函数内部。
闭包的缺点:
(1)由于闭包会使得函数中的变量都被保存在内存中,内存消耗很大,所以不能滥用闭包,否则会造成网页的性能问题,在IE中可能导致内存泄露。解决方法是,在退出函数之前,将不使用的局部变量全部删除。
(2)闭包会在父函数外部,改变父函数内部变量的值。所以,如果你把父函数当作对象(object)使用,把闭包当作它的公用方法(Public Method),把内部变量当作它的私有属性(private value),这时一定要小心,不要随便改变父函数内部变量的值。

本文就为大家介绍这里,如果大家对javascript闭包还是不够了解,请阅读相关文章进行补充学习,谢谢大家的阅读。

Javascript 相关文章推荐
js编码之encodeURIComponent使用介绍(asp,php)
Mar 01 Javascript
JavaScript实现在标题栏上显示当前日期的方法
Mar 19 Javascript
jQuery UI插件自定义confirm确认框的方法
Mar 20 Javascript
jQuery插件slider实现拖动滑块选取价格范围
Apr 30 Javascript
Angular.JS学习之依赖注入$injector详析
Oct 20 Javascript
Vue.js中extend选项和delimiters选项的比较
Jul 17 Javascript
微信小程序开发animation心跳动画效果
Aug 16 Javascript
JavaScript事件发布/订阅模式原理与用法分析
Aug 21 Javascript
layui使用数据表格实现购物车功能
Jul 26 Javascript
Vue 实现CLI 3.0 + momentjs + lodash打包时优化
Nov 13 Javascript
浅谈Vue 自动化部署打包上线
Jun 14 Javascript
vue实现简易音乐播放器
Aug 14 Vue.js
jQuery检测滚动条是否到达底部
Dec 15 #Javascript
js实现根据身份证号自动生成出生日期
Dec 15 #Javascript
浅析javascript的return语句
Dec 15 #Javascript
轻松学习Javascript闭包函数
Dec 15 #Javascript
Javascript基于AJAX回调函数传递参数实例分析
Dec 15 #Javascript
javascript实现html页面之间参数传递的四种方法实例分析
Dec 15 #Javascript
js编写贪吃蛇的小游戏
Aug 24 #Javascript
You might like
PHP中将数组转成XML格式的实现代码
2011/08/08 PHP
php中$美元符号与Zen Coding冲突问题解决方法分享
2014/05/28 PHP
PHP实现将HTML5中Canvas图像保存到服务器的方法
2014/11/28 PHP
HTML5之WebSocket入门3 -通信模型socket.io
2015/08/21 Javascript
JS拖拽组件学习使用
2016/01/19 Javascript
动态加载js文件简单示例
2016/04/21 Javascript
全面了解JavaScript对象进阶
2016/07/19 Javascript
Bootstrap实现的标签页内容切换显示效果示例
2017/05/25 Javascript
jQuery 控制文本框自动缩小字体填充
2017/06/16 jQuery
[原创]jquery判断元素内容是否为空的方法
2018/05/04 jQuery
mac上配置Android环境变量的方法
2018/07/08 Javascript
JavaScript基础教程之如何实现一个简单的promise
2018/09/11 Javascript
简单两步使用node发送qq邮件的方法
2019/03/01 Javascript
详解Nuxt.js 实战集锦
2019/11/19 Javascript
js验证密码强度解析
2020/03/18 Javascript
node.js基础知识汇总
2020/08/25 Javascript
python基础教程之基本数据类型和变量声明介绍
2014/08/29 Python
Python中的Matplotlib模块入门教程
2015/04/15 Python
python实现在字符串中查找子字符串的方法
2015/07/11 Python
梯度下降法介绍及利用Python实现的方法示例
2017/07/12 Python
Python爬虫实现验证码登录代码实例
2019/05/10 Python
Python Web版语音合成实例详解
2019/07/16 Python
python 函数中的参数类型
2020/02/11 Python
在对linux系统分区进行格式化时需要对磁盘簇(或i节点密度)的大小进行选择,请说明选择的原则
2012/01/13 面试题
如何写一个自定义标签
2012/12/28 面试题
幼儿园英语教学反思
2014/01/30 职场文书
广告设计应届生求职信
2014/03/01 职场文书
物理课外活动总结
2014/08/27 职场文书
丧事答谢词
2015/01/05 职场文书
2015年考研复习计划
2015/01/19 职场文书
2015年大学班长个人工作总结
2015/04/24 职场文书
拉贝日记观后感
2015/06/05 职场文书
2016年教师学习廉政准则心得体会
2016/01/20 职场文书
《别在吃苦的年纪选择安逸》读后感3篇
2019/11/30 职场文书
多表查询、事务、DCL
2021/04/05 MySQL
Java基础之线程锁相关知识总结
2021/06/30 Java/Android