Promise,我是这么理解的!

您所在的位置:网站首页 fullfilled的意思 Promise,我是这么理解的!

Promise,我是这么理解的!

#Promise,我是这么理解的!| 来源: 网络整理| 查看: 265

一、promise不是承诺

Promise在英语里有希望、承诺之意,在Javascript,它是异步解决方案。有人质疑已经有了更高级异步解决方案async/await,还有必要了解promise?是的,因为大部分项目异步方案使用promise,除此之外,promise也是实现async/await的基础。最重要的,promise仍是前端面试热点。

Promise:统一异步操作方法控制器

二、大话promise

如果你看到标题便阅读本文,想必已经了解promise基础知识!

1、resolve不是完成

阮老师课程有句话,“为了行文方便,本章后面的resolved统一只指fulfilled状态”,说明resolved并不一定是代表完成。

//终于排到队了.... function bookDinner(msg) { return new Promise((resolve, reject) => { resolve(msg) }).then(msg => console.log("完成订单:", msg)) .catch(msg => console.log("订单异常:", msg)) }复制代码

上例为举例排队订餐场景,排队过程中状态是pending。排到你后,收银台收银并给你一个号牌,需要等待取餐,这个时候状态便是resolved,收银台仅仅给了你一个订餐成功的承诺,人家比一定保证你能吃上。一旦发生异常或者其他事件,仍可能导致订单失败。

bookDinner(Promise.reject("厨师带着老板娘跑了!"))//'订单异常: 厨师带着老板娘跑了!'复制代码

resolved不能代表fullfilled!

2、希望用不到的catch

上例中我们使用Promise构造函数创建promise实例,并赋予了实例不能改变的状态。在执行任务中我们使用到了catch方法,用于指定状态为rejected或发生错误的回调函数。

catch方法是then(null,rejection)或者then(undefined,rejection)的别名,那为什么会有catch方法?

感官上更接近try/catch方法,代码易读;捕捉错误的能力,catch可以捕捉到前面promise对象(then方法也是promise对象)的错误; let p = new Promise((resolve, reject) => { resolve() }) //第一种: p.then(() => { throw new Error('rejected') }) .catch(v => console.log(v)) // "Error: rejected" //第二种: p.then(() => { throw new Error('rejected') }, v => console.log(v)) //报错复制代码 catch方法只能捕获其前的错误; let p = new Promise((resolve, reject) => { resolve() }) p.catch(err => console.log(err)) .then(() => { throw new Error('catch后的报错') })//报错获取不到复制代码 catch方法报错可以在下一个catch方法获取,因为catch是then的变形。 let p = new Promise((resolve, reject) => { reject() }) p.catch(() => { throw new Error('catch后的报错') }) .catch(err => console.log(err)) //'Error: catch后的报错'复制代码

Promise 对象抛出的错误不会传递到外层代码,即不会影响其他任务正常执行,通俗的说法就是“Promise 会吃掉错误”。

console.log('start....') let p = new Promise((resolve, reject) => { console.log('promise') throw new Error("是否会影响其他代码?") }) p.then(v => console.log(v)) console.log('end!') // start.... // promise // end! //报错:Uncaught (in promise) Error: 是否会影响其他代码?复制代码 3、高要求Promise.all

promise.all([]):数组内所有promise实例状态均为fullfilled,数组promise容器才为fullfilled。数组只要有一个状态rejected,数组promise容器状态九尾rejected。

这个方法确实挺有意思,还是以咱们点餐为例,食物和勺子都得具备才完成吃饭的任务,吃饭状态才能是fullfilled。任何一项不满足的话,对于吃饭任务来说,状态便是rejected。

//获得食物 function getFood() { return Promise.resolve("盖饭") } //获得勺子 function getSpoon() { return Promise.resolve('勺子') } //吃饭 function eatFood() { return Promise.all([getFood(), getSpoon()]) } eatFood().then(v => console.log('吃饭:',v))//'吃饭:["盖饭", "勺子"]' .catch(err => console.log(err)) 复制代码

如果作为参数的 Promise 实例,自己定义了catch方法,那么它一旦被rejected,并不会触发Promise.all()的catch方法。

上边的例子我们稍加改变,服务员迟迟不给你拿勺子,这个时候,针对getSpoon这个任务报了个错,服务员立马知道了,拿来勺子,让你完成吃饭任务。其实是catch方法返回了一个新的实例。

//获得食物 function getFood() { return Promise.resolve("盖饭") } //获得勺子 function getSpoon() { return Promise.reject('还没给勺子') } let getSpoonAgin = getSpoon().then(v => v).catch(err => console.log(err)) //吃饭 function eatFood() { return Promise.all([getFood(), getSpoonAgin]) } eatFood().then(v => console.log("吃饭:", v)) //'吃饭:["盖饭", undefined]' .catch(err => console.log("未能吃饭:", err)) }复制代码 4、竞争上岗Promise.race

promise.race:与promise.all类似,参数也是promise实例数组。哪个promise实例优先"到达",promise.race容器的状态就是先到达的promise实例状态。

继续点餐的例子,大家工作比较忙,中午只能等待15分钟,为了吃上饭你点了两份饭,毕竟胃容量有限,只能哪份先来就吃哪份(杠精们,不要抬杠哈!)当然此处只是举了两个任务状态都是fullfilled的例子。

function getFood1() { return Promise.resolve("盖饭") } function getFood2() { return Promise.resolve('饺子') } function eatFood() { return Promise.race([getFood1(), getFood2()]) } eatFood().then(v => console.log("吃饭:", v)) //'吃饭: 盖饭' .catch(err => console.log("未能吃饭:", err))复制代码 三、写在最后

以上只是针对Promise运行方式以及部分方法进行说明,在项目实战中Promise的使用远比上边所说的例子复杂,希望本篇对于您理解promise异步解决方案有所帮助。

具体在使用中细节可以学习阮一峰老师ES6课程。

如果想要了解任务执行顺序的,可阅读聊聊前端面试之输出顺序

谢谢您的阅读,请多指教!



【本文地址】


今日新闻


推荐新闻


CopyRight 2018-2019 办公设备维修网 版权所有 豫ICP备15022753号-3