async-await如何在Javascript中工作?

时间:2018-12-11 09:40:35

标签: javascript async-await ecmascript-2017

使函数异步是否使其异步?

我开始使用async-await代替Promise链。我做了类似的事情

async function f(){
    let r = await first();
    let d = await sec(r);
    return d;
}

调用此函数后,我能够看到所有代码都是异步发生的。但是在一些较老的文章中,我读到我们无法在javascript中创建异步函数。使函数异步也会使其异步。

4 个答案:

答案 0 :(得分:2)

  

使函数异步是否使其异步?

否,它使它返回一个Promise,并会在该Promise遇到await语句时暂停该功能,直到Promise解析。

提供了一种管理异步代码的方法,但不要停止同步,阻止代码被同步或阻止。

答案 1 :(得分:2)

  

使函数异步是否使其异步?

不,不是。

是的,我们无法在javascript中创建异步函数。在执行异步任务之后,我们可以使用异步函数执行代码,但是代码只能在我们的单线程中执行。

await在async-await中是异步的,当编译器到达await时,它将停止执行并将所有内容推送到事件队列中,并在async函数之后继续执行同步代码。例子

function first() {
    return new Promise( resolve => {
        console.log(2);
        resolve(3);
        console.log(4);
    });
}

async function f(){
    console.log(1);
    let r = await first();
    console.log(r);
}

console.log('a');
f();
console.log('b');

由于等待是异步的,因此等待之前的所有其他事情都照常发生

a
1
2
4
b
// asynchronous happens
3

答案 2 :(得分:0)

  

使函数异步是否使其异步?

取决于您所说的异步

让我们考虑一下您的代码的稍有不同的版本:

async function f(){
    let rPromise = first();
    let dPromise = sec(r);
    let r = await rPromise;
    let dPromise = await dPromise;
    return d;
}

在这里,因为我们直到第二个承诺开始之前都不会await,所以两个都可能同时等待(如果first()返回了一个完整的承诺,它们可能不会同时等待足够快)。两者可能同时做事。 rPromise可能在dPromise之前完成,也可能在之后。但是,只有当他们正在做的事情(例如等待来自Web服务的I / O响应)发生在javascript本身之外时,他们才会同时做事。

在其他一些语言/框架中,我们可能期望两个线程在这里运行,可能在不同的内核上。在javascript中,只有一个线程,而实际上在javascript中运行的代码只有一点(而不是javascript正在等待响应的Web访问库,触发延迟的计时器等),在first()sec()中运行,但绝不能同时运行。如果它们在内部进行await处理,而另一方正在对其进行await处理,则返回该处理,直到其他函数完成,才会进行进一步的处理。

这是asynchronous(两者不是按照固定的顺序发生的,其中一个必须先发生在另一个之上)。

虽然不是多线程的,但每个线程中的实际javascript代码不会同时发生,在其他一些情况下也称为asychronous

  

但是在一些较老的文章中,我读到我们无法在javascript中创建异步函数。

首先,直到最近,尽管我们可以通过其他方式创建承诺,但直到最近我们甚至都无法在javascript中创建这种异步代码。

第二,虽然它是异步,但不是来自其他语言和框架的人会认为它是异步的,异步性主要是通过多线程实现的,而多线程既具有javascript所缺乏的功能,又具有它也缺乏的陷阱。

答案 3 :(得分:0)

异步和等待只是编写JavaScript Promises的一种简单方法。但是,在幕后,JavaScript会将代码转换为执行引入Async和Await之前的代码。

内幕,您的代码示例:

async function f(){
  let r = await first();
  let d = await sec(r);
  return d;
}

真正成为以下代码:

function f() {
  return first().then(r => sec(r));
}

或更详细的示例:

function f() {
  return new Promise(
    (resolve, reject) => {
      first().then(
        function(r) {
          return sec(r);
        }
      ).then(
        function(d) {
          resolve(d);
        }
      ).catch(ex) {
        reject(ex);
      }
    }
  );
}

如您所见,您的代码示例更容易阅读。但这可能会造成混淆,因为它看起来像同步是