javascript onclick事件未正确触发

时间:2016-05-28 05:49:30

标签: javascript jquery

我将这个点击事件附加到每个按钮上,当我点击每个按钮时,它会打印出第三个按钮的输出。我不确定发生了什么。

<!DOCTYPE html>
<html>
<head>
  <title>JS Bin</title>
</head>
<body>
  <button>test1</button>
  <button>test2</button>
  <button>test3</button>
</body>
<script>
   var nodes = document.getElementsByTagName('button');
   for (var i = 0; i < nodes.length; i++) {
       nodes[i].addEventListener('click', function() {
       console.log('You clicked element #' + i);
   });
   }
</script>
</html>

当我点击任何按钮时,它正在打印

"You clicked element #3"

4 个答案:

答案 0 :(得分:3)

对此的简单解决方案:

<!DOCTYPE html>
<html>
<head>
  <title>JS Bin</title>
</head>
<body>
  <button>test1</button>
  <button>test2</button>
  <button>test3</button>
</body>
<script>
   var nodes = document.getElementsByTagName('button');
   console.log(nodes);
   for (var i = 0; i < nodes.length; i++) {
       //converted click function into an IIFE so it executes then and 
        there only
       nodes[i].addEventListener('click', (function(j) {
        return function(){
            console.log('You clicked element #' + j);       
        }

   })(i));
   }
</script>
</html>

你应该通过两个概念来理解这个东西

1)闭包

2)Javascript是单线程和同步的。那么它如何处理事件?

以下是您的代码中发生的事情:

==&GT; for循环同步执行,因为它是javascript处理事件队列的javascript引擎帖子的一部分,这是一个FIFO(先进先出)

==&GT;当for循环结束时,i的值为3,它保留在内存中直到其内部的函数执行

==&GT;每次取值3并打印出来。

答案 1 :(得分:1)

这是一个循环问题中的函数闭包。

JavaScript closure inside loops – simple practical example

注意这一点!

附注:在访谈中经常会询问有关此问题的问题,以证明对JS的熟练程度。

答案 2 :(得分:1)

当此button正在侦听事件时,i的值为nodes.length -1,即2。因为循环已经完成了它的执行并且已将i的值设置为2。

所以它正在安慰You clicked element #3

由于scope&amp; closure

创建IIFE并传递i

的值

希望此代码段有用

  var nodes = document.getElementsByTagName('button');
   for (var i = 0; i < nodes.length; i++) {
   (function(i){
   nodes[i].addEventListener('click', function() {
       console.log('You clicked element #' + i);
   });
}(i))

   }

选中此jsfiddle

答案 3 :(得分:1)

这是使用jQuery的其他方式。

$("button").each(function(e) {
    $(this).data("number", e);
}).bind("click", function(e) {
    console.log("You clicked element #" + $(this).data("number"));
});

https://jsfiddle.net/ChaHyukIm/uxsqu70t/3/