浅谈JavaScript for循环 闭包_javascript技巧

有个网友问了个问题,如下的html,为什么每次输出都是5,而不是点击每个p,就alert出对应的1,2,3,4,5。

<html >
<head>
<meta http-equiv="Content-Type" content="text/html; charset=utf-8" />
<title>闭包演示</title>
<script type="text/javascript">   

function init() {
  var pAry = document.getElementsByTagName("p");
  for( var i=0; i<pAry.length; i++ ) {
     pAry[i].onclick = function() {
     alert(i);
  }
 }
}
</script>
</head>
<body onload="init();">
<p>产品一</p>
<p>产品二</p>
<p>产品三</p>
<p>产品四</p>
<p>产品五</p>
</body>
</html>  

解决方式有以下几种

1、将变量 i 保存给在每个段落对象(p)上

function init() {
 var pAry = document.getElementsByTagName("p");
 for( var i=0; i<pAry.length; i++ ) {
   pAry[i].i = i;
   pAry[i].onclick = function() {
    alert(this.i);
   }
 }
}

2、将变量 i 保存在匿名函数自身

function init2() {
 var pAry = document.getElementsByTagName("p");
 for( var i=0; i<pAry.length; i++ ) {
  (pAry[i].onclick = function() {
    alert(arguments.callee.i);
  }).i = i;
 }
} 

3、加一层闭包,i以函数参数形式传递给内层函数

function init3() {
 var pAry = document.getElementsByTagName("p");
 for( var i=0; i<pAry.length; i++ ) {
  (function(arg){
    pAry[i].onclick = function() {
     alert(arg);
    };
  })(i);//调用时参数
 }
}

4、加一层闭包,i以局部变量形式传递给内存函数

function init4() {
 var pAry = document.getElementsByTagName("p");
 for( var i=0; i<pAry.length; i++ ) {
  (function () {
   var temp = i;//调用时局部变量
   pAry[i].onclick = function() {
    alert(temp);
   }
  })();
 }
}

5、加一层闭包,返回一个函数作为响应事件(注意与3的细微区别)

function init5() {
 var pAry = document.getElementsByTagName("p");
 for( var i=0; i<pAry.length; i++ ) {
  pAry[i].onclick = function(arg) {
    return function() {//返回一个函数
    alert(arg);
   }
  }(i);
 }
}

6、用Function实现,实际上每产生一个函数实例就会产生一个闭包

function init6() {
  var pAry = document.getElementsByTagName("p");
  for( var i=0; i<pAry.length; i++ ) {
   pAry[i].onclick = new Function("alert(" + i + ");");//new一次就产生一个函数实例
  }
}

7、用Function实现,注意与6的区别

function init7() {
  var pAry = document.getElementsByTagName("p");
  for( var i=0; i<pAry.length; i++ ) {
     pAry[i].onclick = Function('alert('+i+')')
  }
}  

以上就是小编为大家带来的浅谈JavaScript for循环 闭包全部内容了,希望大家多多支持~

以上是小编为您精心准备的的内容,在的博客、问答、公众号、人物、课程等栏目也有的相关内容,欢迎继续使用右上角搜索按钮进行搜索javascript
循环闭包
javascript 循环 闭包、闭包浅谈、javascript 闭包、javascript闭包详解、javascript闭包面试题,以便于您获取更多的相关知识。

时间: 2024-10-01 14:18:37

浅谈JavaScript for循环 闭包_javascript技巧的相关文章

浅谈javascript中的闭包_javascript技巧

很长一段时间不理解闭包,后来了解了作用域,以及this相关问题才理解了闭包相关知识. 闭包(closure),也是面试题常客.简单点来说就是函数嵌套函数. 函数作为返回值: function foo () { var a = 1; return function () { a++; console.log(a); } } var aaa = foo(); aaa(); //2 aaa(); //3 其实这个代码不难理解,aaa是指向foo()返回的一个新函数,但是在这个函数里面引用了a变量,所以

浅谈Javascript数组的使用_javascript技巧

上一篇说了数组的索引,这一篇说下数组的使用. 数组的大小 js的数组可以动态调整大小,更确切点说,它没有数组越界的概念,a[a.length]没什么问题.比如声明一个数组a = [1, 3, 5],现在的数组大小是3,最后一个元素的索引是2,但是你依然可以使用a[3],访问a[3]返回的是undefined,给a[3]赋值:a[3] = 7,是给数组a添加了一个元素,现在数组a的长度是4了.你可以试试把下面这段代码放到浏览器里运行下: var a = []; for(int i = 0; i <

浅谈javascript的Touch事件_javascript技巧

js的touch事件,一般用于移动端的触屏滑动 复制代码 代码如下: $(function(){document.addEventListener("touchmove", _touch, false);}) function _touch(event){alert(1);} touchstart:当手指触摸屏幕时触发:即使已经有一个手指放在了屏幕上也会触发. touchmove:当手指在屏幕上滑动时连续的触发.在这个事件发生期间,调用preventDefault()可阻止滚动. to

浅谈javascript中replace()方法_javascript技巧

定义和用法 replace() 方法用于在字符串中用一些字符替换另一些字符,或替换一个与正则表达式匹配的子串.语法stringObject.replace(regexp/substr,replacement) 返回值 一个新的字符串,是用 replacement 替换了 regexp 的第一次匹配或所有匹配之后得到的.说明 字符串 stringObject 的 replace() 方法执行的是查找并替换的操作.它将在 stringObject 中查找与 regexp 相匹配的子字符串,然后用 r

浅谈javascript中自定义模版_javascript技巧

/** * Created by Administrator on 15-1-19. */ function functionUtil() { } functionUtil = { //某个DOM节点是否有某个属性 hasAttr: function (el, name) { var attr = el.getAttributeNode && el.getAttributeNode(name); return attr ? attr.specified : false }, //根据cla

浅谈JavaScript之事件绑定_javascript技巧

其实没有什么新的知识点,只是为了方便其他有需要的朋友们翻阅,对自己而言也算是一个积累,所以只能算是闲谈 JavaScript,老鸟们可以尽情飘过.在进入正题之前,先提个问题热热身吧.现在有如下 HTML 结构: 复制代码 代码如下: <div id="wrap"> <input type="button" value="按钮一" /> <input type="button" value=&quo

浅谈js中的闭包_javascript技巧

首先我们先来看一段代码: 复制代码 代码如下: <a href="javascript:void(0);">111</a> <a href="javascript:void(0);">222</a> <a href="javacsript:void(0);">333</a> var a=document.getElementsByTagName("a");

浅谈javascript的原型继承_javascript技巧

请看源码: 复制代码 代码如下: function clone(o) { var F = function(){}; F.prototype = o; return new F(); } 首先看ext(4.1的1896行开始)的原型式继承. 复制代码 代码如下: var TemplateClass = function(){}; var ExtObject = Ext.Object = { chain: function (object) { TemplateClass.prototype =

浅谈javascript实现八大排序_javascript技巧

开学一个月,已经多次梦见笔试出现数据结构算法题,我对数据结构的恐惧已经多于任何"妖魔鬼怪"了.呵呵,看来真的很有必要复习一下常用的数据结构,免得"噩梦"成真. 数据机构等编程基础的重要性不用多说,直接进入正题. 排序算法,分为内部排序和外部排序.内部排序要使用内存,这里只探讨内部排序. 1,插入排序:直接插入排序和希尔排序 2,选择排序:简单选择排序和堆排序 3,交换排序:冒泡排序和快速排序 4,归并排序 5,基数排序 直接插入排序 基本思想:在要排序的一组数,假设