使js闭包立即执行

时间:2015-05-18 13:50:39

标签: javascript jquery

我可以在以下代码中看到一个问题:

var elems = {
    'elem1': 'param1fds',
    'elem2': 'paramaafds2',
    'elem3': 'paramfdsfd3fdsfds'
  };

for (var k in elems) {
  $('#' + k).click(function(e) {
  // k is always elem3 when I click on the element
  // elems[k] == 'paramfdsfd3fdsfds'

当代码执行时,k等于elem3。我该如何处理?

3 个答案:

答案 0 :(得分:6)

标准通用解决方案是在闭包中添加IIFE保护变量:

for (var k in elems) {
   (function(k){
     $('#' + k).click(function(e) {
        // k is always elem3 when I click on the
     })
    })(k);
}

当您使用jQuery时,您还可以使用$.each

$.each(elems, function(k){
     $('#' + k).click(function(e) {

第三种解决方案是使用on并提供data

for (var k in elems) {
    $('#' + k).on('click', {k:k}, function(e) {  
         // use e.data.k here

在不久的将来,使用ES6,第四个解决方案将是使用let的块范围变量:

for (let k in elems) {
   $('#' + k).click(function(e) {
      // k is OK

答案 1 :(得分:1)

var elems = {
    'elem1': 'param1fds',
    'elem2': 'paramaafds2',
    'elem3': 'paramfdsfd3fdsfds'
  };

for (var k in elems) {
    (function(elem){
        $('#' + elem).click(function(e) {});
    })(k);
...
}

答案 2 :(得分:0)

我认为现代解决方案是在功能上做,而不是循环:

Object.keys(elems).forEach( function(elKey) {
    $('#' + elems[elKey]).click(function(e) {});
});

这与使用IIFE的结果相同,但我认为更容易理解。