promise?
一、什么是promise?
promise是一个容器,里面保存着某个未来才会结束的事件(通常是一个异步操作)的结果。
从语法上说,promise 是一个对象,从它可以获取异步操作的的最终状态(成功或失败)。
Promise是一个构造函数,这个回调函数中放的是异步的操作,对外提供统一的 API,自己身上有all、reject、resolve等方法,原型上有then、catch等方法。
对于一个异步操作来说执行是需要时间的,所以一开始promise是一个pending初始状态,到了一定的条件就会变成fulfilled(成功)或者reject(失败的状态),在成功时我们执行resolve回调函数,相当于.then里的回调,失败时执行reject回调函数,相当于.catch里的回调。
promise就是把原来的回调函数嵌套在里面的写法变成了链式写法(.then的写法)
promise是es6 中专门用来处理异步回调的,可以解决地狱回调,其中地狱回调指一段代码嵌套了很多层的回调函数。
二、promise的三种状态:①pending 初始状态、②fulfilled 成功状态、③rejected 失败状态,
这三种状态只有异步操作的结果可以决定当前是哪一种状态,其他任何操作都无法改变这个状态。
Promise的状态一旦改变,就不会再变,任何时候都可以得到这个结果,状态不可以逆,只能由 pending变成fulfilled或者由pending变成 rejected。
三、promise的实现是:在构造函数中把回调函数作为参数,回调函数中放的是异步的操作,
一般来说执行异步操作是需要时间,所以一开始promise是一个pending状态,到了一定
的条件就会变成fulfilled(成功)或者reject(失败的状态) ,
成功的时执行resolve回调函数,相当于.then里的回调,
失败的时执行reject回调函数,相当于.catch回调。
promise是把原来的回调函数嵌套在里面的写法变成了链式写法(.then的写法)
四、promise的应用场景:①封装ajax、②axios的get,post封装、③微信小程序中封装wx.request()、④uniapp开发中uni.request()、
五、promose的API:①all()方法: Promise 的 all 方法可以并行执行异步操作,同时在所有异步操作执行完之后才执行回调。
②race()方法:race 字面解释是赛跑的意思。race 的用法与 all 一样,all 是等所有异步操作都执行完毕后才执行 then 回调,race 是只要有一个异步 操作执行完毕,就立刻执行 then 回调。还可以 用 race 给某个异步请求设置超时时间,并且在超时后执行相应的操作。
例如:Promise.race([cutUp(), boil()]).then(function(results){ console.log("哈哈,我先买好啦"); console.log(results); });
③catch()方法:它可以和 then 的第二个参数一样,用来指定 reject 的回调。
④then()方法:把原来的回调写法分离出来,在异步操作执行完后,用链式调用的方式执行回调函数。
在 then 方法中继续写 Promise 对象并返回,然后继续调用 then 来进行回调操作。
例如:
//买笔
function buy(){
console.log("开始买笔");
var p = new Promise(function(resolve,reject){
setTimeout(function(){
console.log("买了笔芯");
resolve("数学作业");
},1000);
});
return p;
}
//写作业
function work(data){
console.log("开始写作业:"+data);
var p = new Promise(function(resolve,reject){
setTimeout(function(){
console.log("写完作业");
resolve("作业本");
},1000);
});
return p;
}
function out(data){
console.log("开始上交:"+data);
var p = new Promise(function(resolve,reject){
setTimeout(function(){
console.log("上交完毕");
resolve("得分:A");
},1000);
});
return p;
}
/* 不建议使用这种方式
buy().then(function(data){
return work(data);
}).then(function(data){
return out(data);
}).then(function(data){
console.log(data);
});*/
//推荐这种简化的写法
buy().then(work).then(out).then(function(data){
console.log(data);
});
async/await?
一、Async 和 await :是一种用同步的写法,执行异步的操作,是es6提出的,两个是搭配使用才会有效。
es7中就是用同步的方式写异步的代码,其中async函数的返回值是一个promise对象。
①.async的用法,它作为一个关键字放到函数前面,这样普通函数就变为了异步函数;
②异步async函数调用,跟普通函数的使用方式一样
③异步async函数返回一个promise对象
④.async函数配合await关键字使用(阻塞代码往下执行)是异步方法,但是阻塞式的;
await 操作符用于等待一个 Promise 对象,只能使用在async声明的函数里,不能使用在普通函数里。
await 在等待 Promise 对象时会导致 async function 暂停执行, 一直到 Promise 对象决议之后才会 async function 继续执行.
二、优点:
①.同步代码编写方式: Promise使用then函数进行链式调用,async/await从上到下,顺序执行,就像写同步代码一样,更符合代码编写习惯;
②.多个参数传递: Promise的then函数只能传递一个参数,async可以同时传递多个参数
③.同步代码和异步代码可以一起编写:当然,异步过程需要包装成一个Promise对象放在await关键字后面;
④.sync/await是对Promise的优化: async/await是基于Promise的,是进一步的一种优化,不过在写代码时,Promise本身的API出现得很少,很接近同步代码的写法;
三、使用场景:async主要来处理异步的操作,可以处理地狱回调,地狱回调是一段代码嵌套了很多层的回调函数。
四、需求:执行第一步,将执行第一步的结果返回给第二步使用。在ajax中先拿到一个接口的返回数据,然后使用第一步返回的数据执行第二步操作的接口调用,达到异步操作。
generator函数?
一、用途:在js中,一个函数一旦被执行,就会执行到最后或是被return,它运行期间不会受到外部的影响,它(generator函数)的出现打破了这种函数运行的完整性。
综上所述,promise、async/await、generator函数都是异步编程解决方案,其中promise是最早出现的,async/await是后出现的,但是是在generator函数出现之后。