将参数传递给ajax onreadystatechange回调?

Bri*_*and 25 javascript ajax

什么是普通的纯javascript(即不是JQuery)将参数传递给匿名onreadystatechange回调的方法?

例如:

function doRequest(){
    /* Get an XMLHttpRequest in a platform independent way */    
    var xhttp = getXmlHttpRequestObject(); 

    var msg="show this message when done"; /* another variable to pass into callback */

     /* How do I pass 'msg' and 'xhttp' into this anonymous function as locals
       named 'x' and 'm'??? */
    xhttp.onreadychangestate=function(x,m)
    {
       if( x.readyState == 4 )
       {
           alert(m);
       }
    }
    /* do the open() and send() calls here.... */
}
Run Code Online (Sandbox Code Playgroud)

Geo*_*rge 32

JavaScript的支持关闭,所以你写的匿名函数将能够访问xhttpmsg从封闭doRequest()范围.

如果想明确地这样做(例如,如果你想在代码中的其他地方定义回调函数并重用它),你可以创建一个创建回调的函数.这也允许您使用不同的名称(例如xm)来为变量设置别名:

function createCallback(x, m) {
    return function() {
        /* Do whatever */
    };
}
Run Code Online (Sandbox Code Playgroud)

然后在doRequest(),做xhttp.onreadystatechange = createCallback(xhttp, msg);

如果您只想"重命名"变量,则可以内联和匿名执行此操作:

xhttp.onreadystatechange = (function(x, m) {
    return function() {
        /* Do stuff */
    }
})(xhttp, msg);
Run Code Online (Sandbox Code Playgroud)

  • 谢谢。这个答案促使我学习了更多关于 Javascript 的知识。我真的只需要知道闭包是如何工作的。 (2认同)

ver*_*zim 15

以上部分答案对我不起作用.首先,对于没有参数的单独callBack函数:

 xhttp.onreadystatechange = callBack;   //works; the function's NAME is required
Run Code Online (Sandbox Code Playgroud)

现在假设修改了callBack函数以接收一些参数:

 xhttp.onreadystatechange = callBack(x,m); //didn't work, and didn't know why
 xhttp.onreadystatechange = createCallback(xhttp,msg); //bad part of above Answer
Run Code Online (Sandbox Code Playgroud)

然而,在StackOverflow的其他地方有人解释说它需要为onreadystatechange分配一个"函数引用"而不是"函数调用"(就像上面的NAME是一个函数引用),并发布了一个解决方案:

 xhttp.onreadystatechange = function(){callBack(x,m);}; //works
Run Code Online (Sandbox Code Playgroud)

我来到这里为其他答案添加一些东西,但现在找不到它.所以我不妨在这里添加它.在我自己的代码中,我使用了局部变量和全局变量,并发现了一些似乎不正常的东西,但现在我知道实际发生了什么,Word Of Warning似乎是合适的.假设"g"是一个全局变量:

 xhttp.onreadystatechange = function(){callBack(x,g);};//anonymous function works
Run Code Online (Sandbox Code Playgroud)

函数引用在某个时间点(T0)分配给onreadystatechange,并且在不同的时间(T1)调用callBack函数.那么,T1处的全局变量"g"的值是传递给callBack函数的值,而不是在T0处分配函数引用时的值"g".别咬我这咬你!(局部变量通常没有这个问题,因为它们通常超出T1的范围,因此在设置匿名函数的参数值时,JavaScript必须在T0使用它们的现有值.)


Sim*_* Hi 9

永远不会太晚!:-)

无需在 xhttp.onreadystatechange 中使用参数传递数据,这有点复杂,您只需向 xhr 对象本身添加属性即可。

例如:

var m = "Hello!";
var xhttp = new XMLHttpRequest();
xhttp.m = m;
xhttp.onreadystatechange = function()
{
    var x, m;
    x = this;
    m = x.m;
    if ((x.readyState == 4) && (x.status == 200))
    {
        alert(m);
    }
};
// ...
Run Code Online (Sandbox Code Playgroud)