一、定义
用于表示一个异步操作的最终状态(完成或失败),以及该异步操作的结果值。
二、宏观任务和微观任务
宏观任务: 宿主(浏览器、node)发起的任务(setTimeout、setInterval、setImmediate、requestAnimationFrame、I/O、UI rendering);
微观任务: JavaScript引擎发起的任务(Promise)。
每个宏观任务都包含一个围观任务队列
- setTimeout等宿主预定义函数,会添加宏观任务
- Promise永远在队列尾部添加微观任务
分析异步执行的顺序:
- 分析有多少个宏观任务;
- 宏观任务中有多少个微观任务;
- 根据调用顺序确定宏观任务中微观任务的执行次序;
- 根据宏观任务的触发规则和调用次序,确定宏观任务的执行次序;
- 确定整个次序
function sleep(timer) {
return new Promise(function (resolve, reject) {
console.log('b');
setTimeout(resolve,timer)
})
}
console.log('a');
sleep(2000).then(()=>console.log('c'))
复制代码
第一个宏观任务先后同步执行了‘a’和‘b’,第二个宏观任务执行调用了resolve,然后then中的代码异步执行得到‘c’
var r = new Promise(function(resolve, reject){
console.log("a");//4、打印a
resolve()//5、等待
});//1、跳过未执行
setTimeout(()=>console.log("d"), 0)//2、宏观任务;8、打印d
r.then(() => console.log("c"));//3、执行r();7、打印c
console.log("b")//6、打印b
复制代码
setTimeout(()=>console.log("d"), 0)
var r = new Promise(function(resolve, reject){
resolve()
});
r.then(() => {
var begin = Date.now();
while(Date.now() - begin < 1000);
console.log("c1")
new Promise(function(resolve, reject){
resolve()
}).then(() => console.log("c2"))
});
复制代码
一秒钟之后执行c1,再执行c2,最后执行宏观任务setTimeout,打印d。
三、async/await
function sleep(duration) {
return new Promise(function(resolve, reject) {
setTimeout(resolve,duration);
})
}
async function foo(){
console.log("a")
await sleep(2000)
console.log("b")
}
foo();
复制代码
foo中调用sleep,按照执行顺序打印a,等待2s后打印b
function sleep(duration) {
return new Promise(function(resolve, reject) {
setTimeout(resolve,duration);
})
}
async function foo(name){
await sleep(2000)
console.log(name)
}
async function foo2(){
await foo("a");
await foo("b");
}
foo2();
复制代码
foo2中调用两次异步函数sleep,2s后Promise执行,打印a,2s后再打印b
*关于vue框架中的axios,因为Axios 是一个基于 promise 的 HTTP 库,所以不必再次调用promise。