Javascript node.js中的管道设置超时

Javascript node.js中的管道设置超时,javascript,node.js,Javascript,Node.js,我正在编写node.js控制台应用程序。我有两个setTimeout函数,如下所示 setTimeout(function(){ process.stdout.write('\n\nJokes Apart !!!\n\n'); }, 2000); setTimeout(function(){ process.stdout.write('\n\nLet\'s play a game !!!\n\n'); }, 1000); 我真正想要的是,第一条信息应该在2秒钟后出现。之后,第

我正在编写node.js控制台应用程序。我有两个setTimeout函数,如下所示

setTimeout(function(){
    process.stdout.write('\n\nJokes Apart !!!\n\n');
}, 2000);

setTimeout(function(){
    process.stdout.write('\n\nLet\'s play a game !!!\n\n');
}, 1000);

我真正想要的是,第一条信息应该在2秒钟后出现。之后,第二条消息应在1秒后出现。但是发生的是,第二条消息在1秒后出现,然后第一条消息出现。由于这两个函数都是异步的,因此会同时调用它们。有没有办法通过管道传输它们?

要了解发生了什么,您应该首先了解JS事件循环及其非阻塞性质。你可以在这里阅读:,或者如果你喜欢视频形式,这是一个很棒的演讲:

简言之,引擎会遍历代码-当遇到第一个
设置超时时,它会对其进行调度(2秒后),然后继续运行。然后它会看到第二个
setTimeout
,并对其进行调度。当第二次调用通过时,将触发并执行来自第二次
setTimeout
的回调,仅在第二次调用后,将触发来自第一次调用的回调。这就是为什么你会这样看他们

现在修复它-您只需将其嵌套即可:

setTimeout(function(){
   process.stdout.write('\n\nJokes Apart !!!\n\n');

   setTimeout(function(){
       process.stdout.write('\n\nLet\'s play a game !!!\n\n');
   }, 1000);
}, 2000);
这会导致第二个
setTimeout
仅在第一个回调运行时被调度。

setTimeout()
在Javascript中没有阻塞。所以,你所做的是安排两个计时器在未来运行。一个从现在开始运行1秒。另一个从现在开始运行两秒钟。因此,你得到了你观察到的行为

您可以将第一个计划从现在开始运行2秒,然后将第一个计划从现在开始运行1秒,然后将第一个计划从现在开始运行3秒

setTimeout(function(){
    process.stdout.write('\n\nJokes Apart !!!\n\n');
}, 2000);

// schedule this one to be 3 seconds from now, which will be 1 second after the prior one
// since that one fired in 2 seconds
setTimeout(function(){
    process.stdout.write('\n\nLet\'s play a game !!!\n\n');
}, 3000);
或者,您可以安排第一个从现在开始运行2秒,然后在该回调中,您可以安排下一个从第一个启动时开始运行1秒

setTimeout(function(){
    process.stdout.write('\n\nJokes Apart !!!\n\n');
        // when the first timer fires, set a new timer to run the second
        // part one second from when the first one fired
        setTimeout(function(){
            process.stdout.write('\n\nLet\'s play a game !!!\n\n');
        }, 1000);
}, 2000);
这种非阻塞特性使Javascript具有异步行为。当您调用第一个
setTimeout()
时,Javascript解释器不会停止并等待计时器启动。相反,它将计时器安排在将来某个时候运行,然后继续执行Javascript的其余部分。在您的代码中,下一行代码是另一个
setTimeout()
,因此它也会立即调度该计时器。因为它们都是在同一时间安排的,所以从现在开始计划2秒的时间比从现在开始计划1秒的时间要晚

因此,你最终有两个选择。您可以更改第二次的时间,使其在您希望启动时启动(假定调度两个计时器的代码基本上是在同一时间运行的),也可以更改当您调度第二个计时器直到第一个计时器启动后的时间