1、 const promise = new Promise((resolve, reject)=>{
console.log(1);
resolve();
console.log(2);
})
promise.then(()=>{
console.log(4);
})
console.log(5);
运行结果是: 1,2,5,4
解释:promise的构造函数是同步执行,promise.then中的函数是异步执行。
2、 const promise = new Promise((resolve, reject) => {
resolve('success1')
reject('error')
resolve('success2')
})
promise
.then((res) => {
console.log('then: ', res)
})
.catch((err) => {
console.log('catch: ', err)
})
运行结果:then: success1
解释:构造函数中的 resolve 或 reject 只有第一次执行有效,多次调用没有任何作用。promise 状态一旦改变则不能再变。 promise 有 3 种状 态: pending、fulfilled 或 rejected。 状态改变只能是 pending->fulfilled 或者 pending-> rejected,状态一旦改变则不能再变。
3、const promise = new Promise((resolve, reject) => {
setTimeout(() => {
console.log('once')
resolve('success')
}, 1000)
})
const start = Date.now()
promise.then((res) => {
console.log(res, Date.now() - start)
})
promise.then((res) => {
console.log(res, Date.now() - start)
})
运行结果: once success 1005 success 1007
解释:promise 的 .then 或者 .catch 可以被调用多次,但这里 Promise 构造函数只执行一次。或者说 promise 内部状态一经改变,并且有了一个值,那么后续每次调用 .then 或者 .catch 都会直接拿到该值。
4、console.log('start');
new Promise(function(resolve,reject){
setTimeout(function(){ //定时器模拟异步
resolve('hello'); //修改promise状态调用then中的第一个函数
},2000);
}).then((value)=>{
console.log(value); //接收resolve传来的值
return new Promise(function(resolve){ //该then()返回一个新的promise实例,后面可以继续接then
setTimeout(function(){
resolve('world'); //修改新promise的状态,去调用then
},3000)
})
}).then((value)=>{
console.log(value);
})
//输出结果: /* 立即输出 start 两秒输出 hello 再三秒 world */
5、上面我们在 then() 函数中返回的是一个新的promise,如果返回的不是一个新的promise会怎样呢?依然是上面的代码,稍作修改。
console.log('start');
new Promise(function(resolve,reject){
setTimeout(function(){
resolve('hello');
},2000);
}).then((value)=>{
console.log(value);
(function(){
return new Promise(function(resolve){
setTimeout(function(){
resolve('world');
},3000)
})
})();
return false;
}).then((value)=>{
console.log(value);
})
/*
结果:
立即输出 start
两秒输出 hello
三秒输出 false
*/
根据上面的运行结果来看,如果在一个then()中没有返回一个新的promise,则return 什么下一个then就接受什么,在上面的实例代码中return的是false,下一个 then中接受到的value就是false,如果then中没有return,则默认return的是 undefined.
6、then()中包含.then()的嵌套情况 then()的嵌套会先将内部的then()执行完毕再继续执行外部的then();在多个then嵌套时建议将其展开,将then()放在同一级,这样代码更清晰。
console.log('start');
new Promise((resolve,reject)=>{
setTimeout(function(){
console.log('step');
resolve(110);
},1000)
})
.then((value)=>{
return new Promise((resolve,reject)=>{
setTimeout(function(){
console.log('step1');
resolve(value);
},1000)
})
.then((value)=>{
console.log('step 1-1');
return value;
})
.then((value)=>{
console.log('step 1-2');
return value;
})
})
.then((value)=>{
console.log(value);
console.log('step 2');
})
/*
start
step
step1
step 1-1
step 1-2
110
step 2
*/
//展开之后的代码
console.log('start');
new Promise((resolve,reject)=>{
setTimeout(function(){
console.log('step');
resolve(110);
},1000)
})
.then((value)=>{
return new Promise((resolve,reject)=>{
setTimeout(function(){
console.log('step1');
resolve(value);
},1000)
})
})
.then((value)=>{
console.log('step 1-1');
return value;
})
.then((value)=>{
console.log('step 1-2');
return value;
})
.then((value)=>{
console.log(value);
console.log('step 2');
})
7、catch和then的连用 如果每一步都有可能出现错误,那么就可能出现catch后面接上then的情况。上代码
new Promise((resolve,reject)=>{
resolve();
})
.then(value=>{
console.log('done 1');
throw new Error('done 1 error');
})
.catch(err=>{
console.log('错误信息1:'+err);
})
.then(value=>{
console.log('done 2');
})
.catch(err=>{
console.log('错误信息2:'+err);
})
/*
done 1
错误信息1:Error: done 1 error
done 2
说明catch后面会继续执行then,catch返回的也是一个promise实例
*/
new Promise((resolve,reject)=>{
resolve();
})
.then(value=>{
console.log('done 1');
throw new Error('done 1 error');
})
.catch(err=>{
console.log('错误信息1:'+err);
throw new Error('catch error');
})
.then(value=>{
console.log('done 2');
})
.catch(err=>{
console.log('错误信息2:'+err);
})
/*
done 1
错误信息1:Error: done 1 error
错误信息2:Error: catch error
如果在catch中也抛出了错误,则后面的then的第一个函数不会执行,因为返回的
promise状态已经为rejected了
8、Promise.all() 将多个Promise批量执行,所有的Promise都完毕之后返回一个新的Promise
1、接收一个数组作为参数
2、数组中可以是Promise实例,也可以是别的值,只有Promise会等待状态的改变
3、所有子Promise完成,则该Promise完成,并且返回值是参数数组中所有Promise实
例的结果组成的数组
4、有任何一个Promise失败,则该Promise失败,返回值是第一个失败的Promise的结果
console.log('here we go');
Promise.all([1,2,3])
.then(all=>{
console.log('1: ' + all);
return Promise.all([function(){
console.log('ooxx');
},'xxoo',false])
})
.then(all=>{
console.log('2: ' + all);
let p1 = new Promise(resolve=>{
setTimeout(function(){
resolve('I\'m p1');
},1500)
});
let p2 = new Promise(resolve=>{
setTimeout(function(){
resolve('I\'m p2');
},2000)
});
return Promise.all([p1,p2]);
})
.then(all=>{
console.log('3: '+all);
let p1 = new Promise((resolve,reject)=>{
setTimeout(function(){
resolve('P1');
},1000)
})
let p2 = new Promise((resolve,reject)=>{
setTimeout(function(){
reject('P2');
},3000)
})
let p3 = new Promise((resolve,reject)=>{
setTimeout(function(){
reject('P3');
},2000)
})
return Promise.all([p1,p2,p3]);
})
.then(all=>{
console.log('all: ' + all);
})
.catch(err=>{
console.log('Catch:' + err);
})
/*
here we go
1: 1,2,3
2: function(){
console.log('ooxx');
},xxoo,false
3: I'm p1,I'm p2
Catch:P3
证明了上面的四点。
*/
9、Promise.race() 和Promise.all()差不多,区别就是传入的数组中有一个Promise完成了则整个Promise完成了。
let p1 = new Promise(resolve=>{
setTimeout(function(){
resolve('p1');
},10000);
})
let p2 = new Promise(resolve=>{
setTimeout(function(){
resolve('p2');
},1000);
})
Promise.race([p1,p2])
.then((value)=>{
console.log(value);
})
/*
p1 1s之后输出
。。 等待十秒后代码才算执行完毕
*/