javascript addEventListener无法按预期工作

时间:2016-08-21 06:36:43

标签: javascript for-loop javascript-events addeventlistener

我正在研究一些常见的JavaScript程序。下面的内容为DOM添加了4个按钮,并为每个按钮添加了一个事件监听器

for(var i =0;i<5;i++){
    var btn = document.createElement('button');
    btn.appendChild(document.createTextNode('Button' + i));

    //function 1
    (function(i){
     btn.addEventListener('click', function(){console.log(i)});
     })(i);

    //function 2 commented
    /*btn.addEventListener('click', (function(i){
     return function(){
     console.log(i);
     }
     })(i));*/

    document.body.appendChild(btn);
}

函数1和函数2都会向按钮添加事件监听器并完美地工作。我想知道,为什么下面的代码没有: -

for(var i =0;i<5;i++){
    var btn = document.createElement('button');
    btn.appendChild(document.createTextNode('Button' + i));

    btn.addEventListener('click', function(){
        console.log('Clicked' + i);
    });
    document.body.appendChild(btn);
}

此代码仅在点击时为每个按钮记录5。为什么会这样,我不明白为什么它不能为每个循环保留i的值?

2 个答案:

答案 0 :(得分:2)

如果您使用var,则Javascript没有块范围。因此,准确使用您的代码,您可以将“预期结果”替换为var的{​​{1}}:

let

答案 1 :(得分:1)

在处理addEventListener循环时eventTarget添加for时,它不会触发侦听器。

它会在稍后阶段触发,此时for-loop已完成执行并更新了i的值。

当你在for-loop内创建一个函数时,它正在创建一个闭包并绑定i的值