我有这个函数,等待异步函数完成它的工作,然后返回。
function synchronous(){
var notYet = true;
setTimeout(function(){
notYet = false;
}, 1000);
while(notYet)
;
return "Done synchronously!";
}
console.log(synchronous());
这里使用synchronous
循环停止函数while
,直到执行异步函数(这里为setTimeout
)的回调。但是,回调永远不会被调用(使用回调中的alert
进行检查),因此,notYet
将保持true
并且函数循环将永远存在。那么,为什么在1000毫秒后没有调用回调呢?
注意:我不关心如何将异步函数转换为同步函数。我的问题是为什么回调没有被调用?
答案 0 :(得分:6)
回调没有被调用,因为可以调用它的唯一线程被束缚在你的无限循环中。
在浏览器中,JavaScript在单个主UI线程上运行(加上您想要创建的Web工作者数量)。该线程在作业队列上运行:它获取要执行的作业(例如,处理单击),完成作业,然后返回以等待下一个作业。你用无限循环来阻止那个线程。计时器调度作业队列中的回调(可能是特定于实现的),但是线程永远不会完成当前作业(调用无限循环的作业),因此它永远不会接受下一个作业。
NodeJS还在一个线程中运行您的代码,同样的事情也是如此。 (并非所有环境都可以,但我不知道任何setTimeout
没有在请求它的同一线程上安排定时器回调。)