闭包由三个特性
1.函数嵌套函数
2.函数内部可以引用外部的参数和变量
3.参数和变量不会被垃圾回收机制回收
闭包是指有权访问另一个函数作用域中的变量的函数,创建闭包的最常见的方式就是在一个函数内创建另一个函数,通过另一个函数访问这个函数的局部变量
使用闭包有一个优点,也是它的缺点,就是可以把局部变量驻留在内存中,可以避免使用全局变量。全局变量在每个模块都可调用,这势必将是灾难性的。
嵌套函数的闭包:
function aaa(){ var a=1; return function(){ console.log(a++); } } var fun =aaa(); fun();//1 执行后 a++,,然后a还在~ fun();//2 fun=null;//a被回收
闭包会使变量始终保存在内存中,如果不当使用会增大内存消耗。
javascript的垃圾回收原理
(1)、在javascript中,如果一个对象不再被引用,那么这个对象就会被GC回收;
(2)、如果两个对象互相引用,而不再被第3者所引用,那么这两个互相引用的对象也会被回收。
那么使用闭包有什么好处呢?使用闭包的好处是:
1.希望一个变量长期驻扎在内存中
2.避免全局变量的污染
3.私有成员的存在
模块化代码。减少全局变量污染
var abc = (function(){ //abc为外部匿名函数的返回值 var a = 1; return function(){ a++; alert(a); } })(); abc(); //2 ;调用一次abc函数,其实是调用里面内部函数的返回值 abc(); //3
私有成员的存在
var aaa = (function(){ var a = 1; function bbb(){ a++; alert(a); } function ccc(){ a++; alert(a); } return { b:bbb, //json结构 c:ccc } })(); aaa.b(); //2 aaa.c() //3
下面举一个闭包的例子
点击列表输出索引
容易出错的方法
<script> window.onload = function(){ var aLi = document.getElementsByTagName('li'); for (var i=0;i<aLi.length;i++){
//这里给它一个index就能解决
//aLi[i].index=i+1;
aLi[i].onclick = function(){ //当点击时for循环已经结束,点击输出都是4 alert(this.index); }; } } </script> </head> <body> <ul> <li>123</li> <li>456</li> <li>789</li> <li>010</li> </ul> </body>
闭包实现
<script> window.onload = function(){ var aLi = document.getElementsByTagName('li'); for (var i=0;i<aLi.length;i++){ (function(i){ aLi[i].onclick = function(){ alert(i); }; })(i); } }; </script> </head> <body> <ul> <li>123</li> <li>456</li> <li>789</li> </ul> </body>
一道题目
var test = (function(a) { this.a = a; //先执行2 console.log("a="+a); return function(b) { //先执行3 console.log("b="+b); return this.a + b; } } (function(a, b) { //先执行1 console.log("a="+a); console.log("b="+b); //return的值为传入的a return a; }(1, 2))); console.log(test(4)); //输出什么????