猿问

为什么闭包可以解决js中循环绑定事件的问题?

今天遇到了利用循环给元素绑定事件的问题,相信大家应该都遇到过这个问题。

我的代码

var hint = ["必填,长度为4-18个字符", "", "再次输入相同密码", "格式: example@github.com", ""];

    var inputIDs = ["ip-name", "ip-pwd", "ip-pwd-cfm", "ip-email", "ip-phone"];

    for (var i = 0; i<hint.length; i++) {

        document.getElementById(inputIDs[i]).addEventListener("focus", function (e) {

            var tar = e.target.parentElement.getElementsByClassName("alert")[0];

            tar.innerHTML = hint[i];

        });

    }

    

下面这段代码用闭包来解决的,但是我没看懂,为什么这样调用不会调用到循环结束时i的值了呢?
没有理解这里闭包的用法,有哪位可以解释一下吗?

for (var i = 0; i < 5; i++) { 

    var a = function(v){

        return function(){

            console.log(v)

        }

    }

    document.body.addEventListener('click',a(i))

}


侃侃尔雅
浏览 752回答 1
1回答

开心每一天1111

如果你不使用闭包,你引用的i就是全局作用域(看你的代码没有在一个函数里)里的i。document.getElementById(inputIDs[i])这里的i就是你绑定时候的i,但是当你调用绑定的事件的时候函数体里的i就不再是绑定时候的i而是循环执行完以后的i的值了,其实你能访问到循环执行完了的i的值也有点类似于闭包,函数执行完了,你还能访问还是里声明的变量。但是你使用了闭包就不一样了,document.body.addEventListener('click',a(i))这里把i以参数的形式传入a函数,这时候已经和循环里的i不一样了,他们指向了不同的地址只是值一样,如果这里你传入的参数是个对象类型,闭包函数里的参数就是你这个对象的引用的copy,你在循环下面修改了传入对象的属性,闭包函数里也会相应修改,但是修改对象的引用的话,闭包里则不会改变。
随时随地看视频慕课网APP

相关分类

JavaScript
我要回答