看了一下网上闭包的概念及文章,对于这个问题,自己做一个梳理吧。
这个是我自身第一次碰到闭包的问题
<!DOCTYPE HTML><html><head><meta charset="utf-8"/><title>闭包循环问题</title><style type="text/CSS">p {background:#ccc; width: 300px; height: 100px;}</style></head> <body> <p id="p0">段落0</p> <p id="p1">段落1</p> <p id="p2">段落2</p> <p id="p3">段落3</p> <p id="p4">段落4</p> <script type="text/Javascript">for( var i=0; i<5; i++ ) { document.getElementById("p"+i).onclick=function() { alert(i); //访问了父函数的变量i, 闭包 };};</script> </body> </html>
如果你以前没这么用过的话,估计也会认为单击某个段落就会弹出这个段落相应的编号0,1,2,3,4。但实际上是都是弹出5;
对于这个问题网上已经有很多讨论的博客了,他们给出了很多方法去实现弹出对应的编号。
var pAry = document.getElementsByTagName("p"); for( var i=0; i< 5; i++ ) { pAry[i].no = i; pAry[i].onclick = function() { alert(this.no); } };
function test() { var pAry = document.getElementsByTagName("p"); for( var i=0; i< pAry.length; i++ ) { (function(arg){ pAry[i].onclick = function() { alert(arg); }; })(i);//调用时参数 } }();
对于这个产生的闭包问题,网上的说法是“变量i是以指针或者变量地址方式保存在函数中”;好吧,都和指针扯上关系了。。。。那就再探索一下吧。
(function test() { var temp =10; for(var i=0; i< 5; i++ ){ document.getElementById("p"+i).onclick=function() { alert(temp); //访问了父函数的变量temp, 闭包 }};temp=20;})();
(function test() { var temp =10; for( var i=0; i< 5; i++ ) { document.getElementById("p"+i).onclick=function() { alert(temp); //访问了父函数的变量i, 闭包 }if(i===1){alert(temp);}};temp=20;})();
// js闭包this对象1var name = 'The Window';var object = { name : 'My Object', getNameFunc1 : function(){ // return this.name; console.log(this);//object return function(){//闭包,访问的便是全局变量的了,this指windows console.log(this);//windows return this.name; //The Window } }, getNameFunc2 : function(){ return this.name;//访问的是object }, aa:function(){ alert(22); }};alert(object.getNameFunc1()());//弹出“The Window”
// js闭包this对象2var name = 'The Window';var object = { name : 'My Object', getNameFunc : function(){ var that = this; console.log(this);//输出的是object return function(){ console.log(this);//输出的仍然是Windows return that.name; }; }};alert(object.getNameFunc()());//弹出“My Object”
写了那么多闭包的东西,那也顺便再说一下闭包有神马用处吧;不然,一直捣乱那闭包可真是一个不好的家伙呢。
看这样一典型的闭包的例子:
function A(){ var a=1; function B(){ return a; }; return B;};var C=A();//C取得A的子作用域B的访问接口console.log(C());//1 C能访问到B的父级作用域中的变量a
只要其他作用域能取到子作用域的访问接口,那么其他作用域就有方法访问该子作用域父级作用域的变量了。这样的话,如果以后需要访问某个函数里面的值得时候,就大大的有用咯。
新闻热点
疑难解答