探究JavaScript闭包
什么是JavaScript闭包?
刚开始知道这个词,就误以为是自动执行的匿名函数块。
比如说+function(){}();
然而并不是,那么请看下面的例子:
function init() {
var name = "initial";
function displayName() {//displayName() is the inner function, a closure
alert(name);
}
displayName();
}
init();
displayname()是闭包吗?函数内部访问函数成员局部属性的方法?
This is an example of lexical scoping: in JavaScript, the scope of a variable is defined by its location within the source code (it is apparent lexically) and nested functions have access to variables declared in their outer scope
这是一个词法域的例子:Javascript中,变量的作用域由他所在的代码区域(明显的词法上的),和可以访问外部作用域的嵌套方法组成。
闭包Closure
再看这个例子:
function makeFunc() {
var name = "Mozilla";
function displayName() {
alert(name);
}
return displayName;
}
var myFunc = makeFunc();
myFunc();
What’s different — and interesting — is that the displayName() inner function was returned from the outer function before being executed.
不同并且有趣的地方是:内部方法displayName在函数外面被return出来,还是在执行之前。
那么可以大胆的说:myFunc就是一个闭包。
A closure is a special kind of object that combines two things: a function, and the environment in which that function was created.
闭包就是一个包含了两个东西的特殊对象:一个方法和创建这个方法的环境。
再看看一个例子 :
function makeAdder(x) {
return function(y) {
return x + y;
};
}
var add5 = makeAdder(5);
var add10 = makeAdder(10);
console.log(add5(2)); // 7
console.log(add10(2)); // 12
显然add5和add10各自都有各自的环境,所持有的变量是不同的。
看一个闭包引起的错误,比较难理解透。
function showHelp(help) {
document.getElementById('help').innerHTML = help;
}
function setupHelp() {
var helpText = [
{'id': 'email', 'help': 'Your e-mail address'},
{'id': 'name', 'help': 'Your full name'},
{'id': 'age', 'help': 'Your age (you must be over 16)'}
];
for (var i = 0; i < helpText.length; i++) {
var item = helpText[i];
document.getElementById(item.id).onfocus = function() {
showHelp(item.help);
}
}
}
setupHelp();
如果有三个输入框,那么每个框点击都会导致#help的内容变成Your age (you must be over 16)。
原因是:赋值给document.getElementById(item.id).onfocus
的function是个闭包函数:,这里循环创建了三个闭包,但是他们共享了同一个外部作用域,也就是setupHelp,那么自然循环结束的时候,onfocus 里面就是指向了数据的最后一个元素。
这些话并不太容易让人相信。
我debug跟踪了一下:
循环走完的时候,onfocus function(){}里面 item 的id已经是’age’,help是
‘Your age (you must be over 16)’
三个input对象都是onfocus绑定了同一个闭包(等同于同一个,环境里变量和函数行为都一样)。
闭包性能
通常一个函数执行完毕之后它内部的局部变量就已经不能再访问了。
而闭包需要维持他所被创建时的作用域环境,过分使用闭包对速度上的性能和内部的消耗是有影响的。没必要的时候不要使用闭包。
本文引用自:https://developer.mozilla.org/en-US/docs/Web/JavaScript/Closures
探究JavaScript闭包的更多相关文章
- JavaScript闭包深入解析
for (var i=1; i<=5; i++) { setTimeout( function timer() { console.log( i ); }, i*1000 ); } --上面这段 ...
- Javascript闭包的一些研究
原文:Javascript闭包的一些研究 本文不谈闭包的概念,因为概念容易把人搞晕,本文希望通过几个鲜活的例子来探究闭包的性质,相信对理解闭包会有所帮助. 程序1 var f = (function( ...
- 《Web 前端面试指南》1、JavaScript 闭包深入浅出
闭包是什么? 闭包是内部函数可以访问外部函数的变量.它可以访问三个作用域:首先可以访问自己的作用域(也就是定义在大括号内的变量),它也能访问外部函数的变量,和它能访问全局变量. 内部函数不仅可以访问外 ...
- JavaScript 闭包深入浅出
闭包是什么? 闭包是内部函数可以访问外部函数的变量.它可以访问三个作用域:首先可以访问自己的作用域(也就是定义在大括号内的变量),它也能访问外部函数的变量,和它能访问全局变量. 内部函数不仅可以访问外 ...
- JavaScript闭包(Closure)
JavaScript闭包(Closure) 本文收集了多本书里对JavaScript闭包(Closure)的解释,或许会对理解闭包有一定帮助. <你不知道的JavsScript> Java ...
- Javascript闭包和C#匿名函数对比分析
C#中引入匿名函数,多少都是受到Javascript的闭包语法和面向函数编程语言的影响.人们发现,在表达式中直接编写函数代码是一种普遍存在的需求,这种语法将比那种必须在某个特定地方定义函数的方式灵活和 ...
- javascript闭包理解
//闭包理解一 function superFun(){ var _super_a='a'; function subfuc(){ console.log(_super_a); } return su ...
- Javascript闭包深入解析及实现方法
1.什么是闭包 闭包,官方对闭包的解释是:一个拥有许多变量和绑定了这些变量的环境的表达式(通常是一个函数),因而这些变量也是该表达式的一部分.闭包的特点:1. 作为一个函数变量的一个引用,当函数返回时 ...
- javascript闭包和作用域链
最近在学习前端知识,看到javascript闭包这里总是云里雾里.于是翻阅了好多资料记录下来本人对闭包的理解. 首先,什么是闭包?看了各位大牛的定义和描述各式各样,我个人认为最容易一种说法: 外部函数 ...
随机推荐
- 解决微信小程序开发中wxss中不能用本地图片
微信小程序开发中wxss中不能用本地图片,我们可以用将我们的图片传到服务器上,然后直接引用在线地址.但是当我们没有服务器时,我们可以用"图床",这个具体可以百度.这里我们用第二种方 ...
- Educational Codeforces Round 72 (Rated for Div. 2)
https://www.cnblogs.com/31415926535x/p/11601964.html 这场只做了前四道,,感觉学到的东西也很多,,最后两道数据结构的题没有补... A. Creat ...
- 在vue项目中使用less
1.安装 less 和 less-loader. 命令: npm install less less-loader --save-dev 2.打开 build/webpack.ba ...
- python学习笔记之zipfile模块
为什么学习: 在做自动化测试平台的apk上传功能部分时候,涉及到apk上传后提取apk的icon图标,通过aapt解析apk,获取对应icon在apk中的地址,通过python的zipfile模块来解 ...
- Spring 梳理 - 构造web项目时,使用eclipse如何引用jar包
方法1:直接将jar复制到web项目中的WEB-INF/lib目录中 方法2:构造buildpath时,不使用“外部jar”的形式
- Spring MVC-从零开始-第一个控制器(不考虑命名规范)
1.目录结构 (log4j.properties.mybatis-config.xml可忽略) 2.配置web.xml文件 <?xml version="1.0" encod ...
- java 队列和栈及示例
一.栈的实现: 1.Stack实现 接口实现: class Stack<E> extends Vector<E> {......} 常用的api函数如下: boolean is ...
- volatile 关键字的作用
简介Java 语言提供了一种稍弱的同步机制,即 volatile 变量,用来确保将变量的更新操作通知到其他线程.volatile 变量具备两种特性:变量可见性.禁止重排序. 作为同步锁在访问 vola ...
- 蓝松短视频SDK支持AE模板, 可做类似微商视频, 小柿饼的效果等
AE模板: 是指设计师用Adobe After Effect做好各种视频动画,比如炫酷视频,文艺/搞笑的场景,相册效果等,根据我们的指导文件导出.蓝松SDK会解析导出的文件,自动还原成AE设计时的动画 ...
- vue运行报错webpack-dev-server: command not found
翻译过来就是: 'webpack-dev-server' 不是内部或外部命令,也不是可运行的程序 解决方法: 然后总结下成功的步骤: 1. 直接在项目目录下: cnpm install npm run ...