【问题标题】:Why does my timeout wait until after the await completes but my log does not?为什么我的超时要等到等待完成后,但我的日志没有?
【发布时间】:2017-07-16 16:59:52
【问题描述】:

如果我有这样的设置:

console.clear();

// noprotect

const fetchSomething = () => new Promise((resolve) => {
    setTimeout(() => resolve('future value'), 500);
});

async function asyncFunction() {
    const result = await fetchSomething();
    console.log('waiting');
    setTimeout(()=>console.log('waiting?'), 250);
    return result + ' 2';
}

asyncFunction().then(result => console.log(result));

我的输出看起来像:

"waiting"
"future value 2"
"waiting?"

我希望waiting? 在结果完成之前执行,但由于某种原因它会等待函数。是什么让一个等待而另一个执行?

【问题讨论】:

    标签: javascript asynchronous ecmascript-6 es6-promise


    【解决方案1】:

    这是异步编程的一个特点。

    您必须添加 await 并使用返回 Promise 的函数包装您的 setTimeout(()=>console.log('waiting?'), 250); 以使其看起来像是被连续评估。

    类似:

    await ((ms) =>{
            console.log('waiting?');
            return new Promise(resolve => setTimeout(resolve, ms));
        })(250);
    

    或者:

    await (() => new Promise(resolve => setTimeout(()=>{
        console.log('waiting?');
        resolve();
    }, 250)))();
    

    请注意,JS 有一个单线程运行时引擎,因此当原始脚本到达结束时它会中断评估。

    setTimeout(function, timeout) 中的函数在第一次有机会且时机成熟时由 JS 评估。

    所以你的函数被中断了两次,又被恢复了两次。

    【讨论】:

    • 你不能等待 setTimeout,因为它不会返回一个承诺。
    • @NineBerry 我添加了可以的示例:)
    【解决方案2】:

    记录“等待?”的调用在await 完成后由setTimeout 启动,所以在fetchSomething 中的500ms 之后已经过去。它只会在fetchSomething 返回后执行 250 毫秒。这足以让asyncFunction 返回。

    如果您想查看不同的行为,请启动计时器以记录“等待?”在调用 await 之前:

    async function asyncFunction() {
      setTimeout(()=>console.log('waiting?'), 250);
      const result = await fetchSomething();
      console.log('waiting');
      return result + ' 2';
    }
    

    【讨论】:

    • 这没有说明为什么会打印“waiting”。
    • @Rob 这个问题没有任何意义。请更具体
    • "waiting" 被打印,但 "waiting?"不是在等待初始化之后
    • @Rob 因为setTimeout所以打印的有点晚
    • 但“等待”会立即打印,“等待?”在“future value2”之后打印
    猜你喜欢
    • 1970-01-01
    • 2017-08-12
    • 2013-01-02
    • 1970-01-01
    • 1970-01-01
    • 2020-06-08
    • 1970-01-01
    • 1970-01-01
    • 2021-09-20
    相关资源
    最近更新 更多