javascript - 将匿名函数传递给具有局部变量的命名函数时,Javascript 中的范围问题

标签 javascript scope attachevent

抱歉标题 - 我想不出一种方式来表达它。

场景如下:

我有一个构建元素的函数:

buildSelect(id,cbFunc,...)

在 buildSelect 内部它是这样做的:

select.attachEvent('onchange',cbFunc);

我还有一个数组:

var xs = ['x1','x2','x3'...];

鉴于所有这些,我有一些代码可以做到这一点:

for(var i = 0; i < xs.length; i++)
{
    buildSelect(blah,function(){ CallBack(xs[i],...) },...);
}

问题是,当 onchange 在其中一个选择上被触发时,它会正确转到 CallBack(),但第一个参数不正确。例如,如果我更改第三个选择,我希望使用 xs[2] 调用 CallBack() 而不是我得到一些不同的东西,如 xs[3] 或其他东西。

如果我稍微修改一下:

for(var i = 0; i < xs.length; i++)
{
    var xm = xs[i];
    buildSelect(blah,function(){ CallBack(xm,...) },...);
}

我仍然在 CallBack() 中得到不正确的值。有些东西告诉我这是范围/闭包相关的,但我似乎无法弄清楚是什么。

我只希望第一个选择调用第一个参数为 xs[0] 的 onchange 回调,第二个选择使用 xs[1] 等等。我在这里做错了什么?

我应该澄清 xs 是一个全局变量。

谢谢

最佳答案

您需要通过在它自己的范围内关闭它来捕获该 xm 值。

为此需要一个单独的函数调用:

buildCallback( curr_xm ) {

      // this function will refer to the `xm` member passed in
    return function(){ CallBack(curr_xm,...) },...);
}

for(var i = 0; i < xs.length; i++)
{
    var xm = xs[ i ];
    buildSelect(blah,buildCallback( xm ),...);
}

现在,回调所指的 xm 就是您传递给 buildCallback 的那个。

如果您需要保留 i 的其他用途,您可以改为发送:

buildCallback( curr_i ) {


      // this function will refer to the `i` value passed in
    return function(){ CallBack( xs[ curr_i ],...) },...);
}

for(var i = 0; i < xs.length; i++)
{
    buildSelect(blah,buildCallback( i ),...);
}

关于javascript - 将匿名函数传递给具有局部变量的命名函数时,Javascript 中的范围问题,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/5024882/

相关文章:

javascript - 在子容器上使用 CSS 转换时,如何在父容器上手动设置溢出大小?

javascript - jquery循环生成的垂直对齐复选框

javascript - 关于 JavaScript 变量作用域的问题

javascript - 解析 json_decode php

javascript - 如何在不使用 bodyParser 中间件的情况下获取 Express 中的 POST 字段?

python - 更新方法内函数内的全局变量

scope - 在 AngularJS 中,如何找到页面上的所有范围?

JavaScript 事件处理程序

javascript - 使用 on() 动态创建的 <li> 元素事件附加不起作用

javascript - 在 Javascript 中使用 addEventHandler 的安全、通用的方法?