感谢您的光临。
我正在为客户端编写一个JavaScript重的应用程序,并且需要一个实用程序函数,我可以传递一个条件和一个回调函数。如果不满足条件,我需要等待几毫秒然后再次测试。如果满足条件,则执行回调。
我已将此方法编写为实用程序类的一部分:
ThreadLocker: function (condition, callback) {
//If condition is true then it resumes running code
if (condition()) {
callback();
} else { //Else it waits 10ms and tries again
setTimeout(Util.ThreadLocker(condition,callback), 10);
}
}
以下是它的使用方法:
var condition = function(){return (myGlobalVariable == "foo") ? true : false;};
var callback = function(){alert("Ready to rock!");};
Util.Threadlocker(condition,callback);
即使我将超时时间设置为10 秒,我也会立即获得堆栈溢出。以下是Chrome给我的信息:
“超出最大调用堆栈大小。”
如果你看一下堆栈,看起来这个函数在一毫秒或两秒内被调用了几十次,即使setTimeOut设置为10秒也是如此。
我在这里做错了什么?
答案 0 :(得分:3)
该行
setTimeout(Util.ThreadLocker(condition,callback), 10);
直接调用'ThreadLocker'函数,没有设置超时。尝试
setTimeout(function () { Util.ThreadLocker(condition,callback); }, 10);
您可能还需要知道,javaScript不是多线程的。它只是在n ms之后调度你的函数,或者只要没有执行其他任何操作就调度你的函数。对于间隔也是如此,如果您创建一个10ms的间隔:任务需要30ms,它将在第10毫秒执行,然后在第40毫秒(从第一个任务完成后)开始执行。
所以你无法真正锁定,但也没有别的东西可以竞争你的代码。
至于堆栈溢出:如果你真的有这种情况,例如。一个递归函数可能会溢出500万行的堆栈(在IE中,Number of Javascript lines executed during page load),你可以使用0的超时来推迟一个函数:
setTimeout(function () { }, 0);
这也是下划线defer工作的方式。