ES7基础——深入理解 async/await

async/await 就是Generator函数的语法糖,只不过它将 * 替换为 async,将 yield 替换为 await,并且它的实现同样离不开Promise。

一、async 函数与 then 命令

1. return返回值

2. 抛出错误

3. Promise的状态变化

二、async 函数与 await 命令

1. return返回值

2. 抛出错误


async 函数返回的是一个 Promise 对象!并且,async 函数的调用并不会造成阻塞,它将内部所有的阻塞都封装在Promise对象中异步执行!

相比Generator函数来说,async/await有如下改进:

(1)内置执行器:async函数和普通函数一样,只需调用就能执行,输出最终结果,不再需要 next 方法

(2)更好的语义:很明显,async用来声明一个函数是异步的,await表示紧跟在后面的表达式需要等待结果。另外,await 也只能出现在 async函数中。

(3)适用性更广:await命令后面跟的可以是Promise对象或原始类型的值(数值、字符串、布尔值,这时会自动转成Promise对象)。

(4)返回值是Promise对象:async函数的返回值是Promise对象,这比Generator函数的返回值Iterator对象方便对了,你可以用then指定下一步操作。进一步的说,async函数完全可以看做多个异步操作包装成的一个Promise对象,而 await 命令就是内部 then 命令的语法糖。

async function func() {
    return new Promise(resolve => {  
        setTimeout(() => {
            resolve('big data');
        }, 1000);
    });
}

async function test () { 
    const data = await func();
    console.log(data);
}

test();  //1秒后输出'big data'

一、async 函数与 then 命令

因为 async函数返回的是一个 Promise对象,因此可以用then命令来处理这个Promise对象。

1. return返回值

如果在函数中 return 了一个直接量,async 会自动把这个直接量通过 Promise.resolve( ) 封装成Promise对象,async中return语句返回的值,则会被then中的回调函数接收,等于回调的参数值,如下所示:

async function f () {
    return 'Yes!';
}

f().then(
    v => console.log('操作成功,',v)  回调函数中的参数v的值等于async函数内的return返回值
);
//操作成功,Yes!

补充,Promise.resolve(x) 可以看作是 new Promise( resolve => resolve(x)) 的简写,用于快速封装字面量对象或其他对象,将其封装成 Promise 实例。

2. 抛出错误

async函数内部抛出的错误,会导致返回的Promise对象变成 reject 状态,抛出的错误会被catch中的回调函数接收。

async function f () {
    throw new Error('出错了'); 
}

f().then(
    v => console.log('操作成功,',v),
    e => console.log('操作失败,',e)  //e就是throw的参数‘出错了’
);
//操作失败,Error:出错了

3. Promise的状态变化

async 函数返回的Promise对象,必须等到函数内部所有的await命令后面的Promise对象都执行完,状态才会改变,才会执行then中的回调函数,除非遇到return语句或throw new Error。

二、async 函数与 await 命令

await 表达式的运算结果取决于它要等的东西。

1. return返回值

正常情况下,await 命令后面跟的是一个Promise对象,也就是在等待一个async函数完成。但是await 命令后面可以跟普通函数或直接量

如果await紧跟的是Promise对象,那await就会阻塞后面代码,等待Promise对象resolve,await的运算结果就是resolve的值;如果不是Promise对象,就直接返回对应的值,不会阻塞。

async function func() {
    return await 123;  //等同于return 123
}

func().then(
    v => console.log(v)
);  
//123

2. 抛出错误

await后面跟的是Promise对象时,如果Promise状态为reject,则reject的参数会被catch中的回调函数接收,并且async函数会中断执行。

async function f() {
    awayt Promise.reject('出错了');
    await Promise.resolve('hello');  //该语句不会执行
}

如果出现1)不想async函数因为reject中断执行 或 2)await后面的异步操作出错,则应该使用 try...catch。

async function f() {
    try {
        await new Promise((resolve, reject) => {
            throw new Error('出错了');
        });
    } catch(e) {

    }
    return await('hello');
}

 

参考资料:

1. 理解 JavaScript 的 async/await

2. async 函数——ES6教程 阮一峰

  • 0
    点赞
  • 1
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值