学习ES6(十):Promise的语法糖await和async

10 篇文章 0 订阅

一、await和async

在ES2017中,引入了async函数,来方便异步操作。

特点

  1. async/await从上到下顺序执行。
  2. async/await可以传递的参数数量不受限制。参数被作为普通局部变量处理,可使用let或者const关键字定义的块级变量。
  3. 同步代码和异步代码可以一起编写,只是要注意异步过程需要包装成一个Promise对象并置于await关键字后面
  4. async/await是对Promise的改进,准确来说是语法糖,本质上还是Promise。

二、使用方法

使用async定义异步处理函数

    async function testAsync(){
        return "hello async"
    }
    console.log(testAsync())
    //Promise { 'hello async' }
    testAsync().then(r=>{
        console.log(r)
    })

我们直接用async关键字定义函数。我们把整个函数执行后的结果打印出来,它直接返回一个Promise对象,可以简便之前定义promise对象的写法,既然返回的是Promise对象,那么就可以直接使用then方法进行下一步操作。这就是被称为语法糖的原因。

而且不仅可以使用then方法,还可以在最后使用捕捉错误的catch方法。

    async function testAsync(){
        return "hello async"
    }
    console.log(testAsync())
    //Promise { 'hello async' }
    testAsync().then(r=>{
    //打印出 hello async
        console.log(r)
        //抛出错误
        throw new Error("this is a mistake")
    }).catch(err=>{
    //捕捉到错误
		console.log(err)
	})

async配合Promise使用

执行下列代码:

function testAsync(){
        return "hello async"
    }
function testPromise(){
        return new Promise((resolve)=>{
            setTimeout(() => {
                resolve("hello Promise")
            }, 3000);
            //resolve("hello Promise")
        })
}
    //await 函数比如放在 async函数里面,await会等待 promise函数执行后resolve后的结果
async function test(){
        var Async_1 = await testAsync()
        var Promise_1 = await testPromise().then()
        console.log(Async_1)
        console.log(Promise_1)
}
test()

运行之后,效果是隔了三秒钟,同时打印。 你可以尝试把setTimeout注释掉,然后把注释的部分取消注释运行。发现也是同时打印

这是为什么呢??

因为await指令如果放在async函数里面,那么该指令会暂停当前异步函数的执行,并等待promise执行,,然后再执行异步函数,并返回结果。如果等待的不是promise对象,则返回该值本身

所以这里的代码执行顺序应该是:

  • test()执行
  • 暂停test()
  • 执行await testAsync
  • 执行 await testPromise().then()
  • 执行test()

因为里面有await关键字,所以要暂停async function test()的执行。等待函数体里面的Promise执行结束后才继续执行。

三、总结

async 和 promise 的写法对比

async function func(){
	return 'hello world'
}
console.log(func())
let p = new Promise((resolve,reject)=>{
	resolve('hello world')
})
console.log(p)

这样写,虽然最后的打印的结果是一样的。但是第二个代码Promise对象的状态已经从pending 变成 fulfilled了,如果在then中抛出一个错误的话,也不会经过错误捕捉操作。从一开始就要决定状态, 然后根据状态去选择执行下一步。使用promise对象,如果第一步没有完成状态的选择,那么不会去执行then中的方法。
如果使用async的话,如果你在then中不抛出错误的话,它会默认按照fulfilled状态一直执行then中的方法,不会固定为fulfilled状态。只要你某个then方法中抛出错误,那么就直接跳过执行catch方法。
所以相比之下还是 async要更方便一点。
这是我下面实验的代码:

    async function func(){
        return 'hello world'
    }
    console.log(func().then(r=>{
        console.log(r)
    }).then(r=>{
        console.log("1")
    }).then(r=>{
        console.log("2")
        throw new Error("这是错误")
    }).then(r=>{
        console.log("3")
    }).catch(err=>{
        console.log(err)
    }))
    let p = new Promise((resolve,reject)=>{
        console.log('1')
        //一开始就要指定状态,如果不使用resolve,那么只会输出1,使用了resolve之后,输出 1 2,即使抛出错误,也无法处理。
        resolve()
        // throw new Error("错误")
    }).then(r=>{
        console.log("2")
    }).catch(err=>{
        // console.log(err)
    })
    console.log(p)
  • 3
    点赞
  • 6
    收藏
    觉得还不错? 一键收藏
  • 0
    评论
promiseasync/await都是用于处理异步操作的方式,但它们在语法和使用上有一些区别。 1. PromisePromiseES6引入的一种处理异步操作的方式。它是一个对象,表示一个异步操作的最终完成(或失败)及其结果的值。Promise提供了一个链式的调用方式,可以通过then()方法来处理异步操作的结果,也可以通过catch()方法来处理异常情况。 2. async/awaitasync/await是ES8引入的一种处理异步操作的方式。它是基于Promise语法糖,使得异步代码看起来更像同步代码。使用async关键字声明一个函数为异步函数,然后在需要等待异步操作结果的地方使用await关键字来等待Promise对象的完成。 区别: - 语法简洁性:async/await相对于Promise更加简洁,更接近于同步代码的写法,使得代码更易读、易理解。 - 错误处理:使用Promise时需要通过catch()方法来捕获异常,而async/await可以使用try/catch语句来处理异常,使得错误处理更加直观。 - 链式调用:Promise通过链式调用的方式来处理多个异步操作,而async/await可以使用同步的方式编写多个异步操作,使得逻辑更加清晰。 - 可读性:async/await相对于Promise更加易于理解和阅读,特别是对于有较多异步操作的代码块。 需要注意的是,async/await是基于Promise的,实际上async函数会返回一个Promise对象。在使用async/await时,可以将任何返回Promise对象的异步操作转化为同步的写法,但在某些情况下可能会导致阻塞。

“相关推荐”对你有帮助么?

  • 非常没帮助
  • 没帮助
  • 一般
  • 有帮助
  • 非常有帮助
提交
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

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

抵扣说明:

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

余额充值