let用来处理循环事件绑定问题的原理分析
来源:互联网 发布:淘宝 唱片 编辑:程序博客网 时间:2024/06/06 20:00
在编写js代码时,有一个问题基本上人人都会遇到,那就是用for循环为一组DOM对象绑定事件响应回调,每个事件回掉函数中i的值都是DOMlist.length。
上代码:
var btns = document.getElementsByTagName('button'); for(var i = 0;i<btns.length;i++){ btns[i].onclick = function () { alert(i); } }
如果为3个按钮绑定事件,不管点击哪个都会弹出 3,这显然是不符合我们的需求的
具体的原因我们下面详叙,先说两种我们经常用到的解决方法:
1.为每个DOM对象添加一个index属性,记录当前的i值
for(var i = 0;i<btns.length;i++){ btns[i].index = i; btns[i].onclick = function () { alert(this.index); } }
2.利用一个自掉用函数将i转换成函数内部变量,再用闭包的原理将内部变量i保存到事件回调函数执行
var btns = document.getElementsByTagName('button'); for(var i = 0;i<btns.length;i++){ (function (i) { btns[i].onclick = function () { alert(i); } })(i) }
以上这两种方法是我们经常应用的,但说实话这两种方法都需要一个逻辑和经验,我们都知道,语言的发展的目标和动力就是为了让编程更简单。ES版本的更新就很好的贯彻了这一理念,那让我们看看ES6中有没有能帮助我们更好解决类似问题的新特性呢。
当然有,不然这篇文章就不会起这个名字了,直接上代码
var btns = document.getElementsByTagName('button'); for(let i = 0;i<btns.length;i++){ btns[i].onclick = function () { alert(i); } }
没错我们只需要把for循环中的var改成let即可。
大家很多都用过或者听说过这种方法,但这种解决方式的原理又是什么呢?这个问题的探究可以让我们更好的理解let的特性和事件响应函数的执行机理。下面就和大家一起探讨一下原因:
*首先,我们先要解释我们为什么会遇到最初的那个问题
那个问题出现的条件是js的三个语言特性(1)js没有块级作用域 (2)事件响应函数通常在非回调函数解析完后执行(这涉及到js引擎解析代码的机制和事件轮询机制)。(3)变量的访问是从当前作用域开始,顺着作用域链向上查找的。这个两个语言特性就造成事件响应函数执行时的i的获取的是全局的(也可能是某个函数作用域中的),就算i是在for循环中定义的也一样。然而此时for循环早就执行完了,i也在多次被赋值后定在btn.length。
*明白了问题出现的原因,我们再来看let有的特性,然后在分析它解决问题的原理:
1.在块作用域有效 2. 在一个作用域内不能重复声明一个变量 3. 不会预处理,不存在变量提升
*此时大家应该都明白,是第一个特性的功劳
如果还没明白,那想必就是对块级作用域的概念还未理解,简单的说块级作用域就是一个{},在这里每一次进入for循环都会有一个循环体{},也就是说在这个例子中有三个相互独立的块级作用域。
let的引入,让块级作用域有了概念,所以此时我们才能说事件响应函数是在某一个块级作用域总定义的。在事件响应函数执行时要访问i,函数作用域中没有i,向上找,此时就不是直接去全局找了,而是被它所在的块级作用域截胡了。
- let用来处理循环事件绑定问题的原理分析
- Js循环绑定事件处理
- 对JQuery在循环中绑定事件的问题理解
- 事件循环的原理
- javascript 循环遍历绑定事件问题
- jQuery 循环 绑定事件 问题记录
- propertychange的绑定事件处理
- js循环绑定事件
- Js绑定事件的问题
- for循环内绑定事件的问题(立即执行与延迟执行)。
- Afinal的IOC原理-通过注解方法是绑定UI和事件源码分析
- DOM2级事件绑定的兼容处理
- WPF 获取绑定的事件处理程序绑定全局资源
- Unity 4.6的使用匿名delegate处理uGUI控件事件绑定的问题
- vue 事件绑定 处理-
- BufferKinfe绑定View的原理分析
- js循环绑定事件解决方案
- js循环绑定事件解决方案
- Android wpa_supplicant源码分析--conf配置文件
- hdu-1312 Red and Black
- 雷子、EVEN和素人的框架
- LDAP 快速入门
- 谷歌2017I/O开发者大会上最有未来的突破
- let用来处理循环事件绑定问题的原理分析
- leetcode 81
- Network
- Network
- Tools
- Android OnClickListener 的三种实现方式
- Network
- C语言 数据结构 线性表 顺序表 线性表的顺序存储结构
- 25张图让你读懂神经网络构架