任务62:PROMISE的基础知识
MDN:https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Guide/Using_promises
https://developer.mozilla.org/zh-CN/docs/Web/JavaScript/Reference/Global_Objects/Promise
1.步骤详解
//promise必须传入executor函数,不传会报错
let p1 = new Promise();
// Uncaught TypeError: Promise resolver undefined is not a function
//在NEW PROMISE的同时就把executor函数执行了
// =>executor函数中有两个默认的形参:resolve/reject 函数
// =>executor函数中一般用来管理一个异步编程(当然只写同步的也可以)
// 每一个PROMISE的实例都有两个重要的信息
// =>[[PromiseStatus]]:PROMISE状态(pending准备状态/resolved(fulfilled)成功状态/rejected失败状态)
// =>[[PromiseValue]]:PROMISE值(一般存放异步编程的处理结果)
// resolve/reject这个两个函数的执行,目的就是改[[PromiseStatus]]/[[PromiseValue]]
// =>一但状态设置为成功或者失败,则不能在改变为其它的
// =>resolve执行是成功 reject执行是失败
// =>执行函数传递的结果就是[[PromiseValue]]
let p1 = new Promise((resolve, reject) => {
setTimeout(_ => {
resolve(100);
reject(200);
}, 1000);
});
//Promise{<resolve>:100}
//_proto_:Promise
//[[PromiseStatus]]:"resolved"
//[[PromiseValue]]:100
//=>>>Promise.resolve(100) 创建一个状态为成功值为100的promise实例
//=>>> Promise.reject(200) 创建一个状态为失败值为200的promise实例
//=>>> Promise.all([promise1,promise2,...]) 所有实例都成功,整体返回的PROMISE实例才是成功,只要有一个失败,整体实例就是失败的
//=>>> Promise.race([promise1,promise2,...]) 多个PROMISE实例同时进行,谁先处理完,以谁的状态作为最后的整体状态(不论是成功还是失败)
let p1 = new Promise((resolve, reject) => {
resolve(100);//<=>Promise.resolve(100) 创建一个状态为成功值为100的promise实例
reject(100);//=>resolve/reject的执行是异步编程,需要等到THEN把方法存放好后,在根据状态通知THRN存放的某个方法执行
});
//P1成功还是失败直接看EXECUTOR函数中执行的是哪个方法
// 每一次执行THEN会返回一个新的POMISE实例 P2也是新的内存地址
// =>不管P1.THEN中哪个方法执行,只要执行不报错,则P2的状态就是成功,相反只要报错,P2就是失败,并且方法返回的结果就是P2的VALUE值
// =>如果P1.THEN中某个方法的执行,返回的是一个新的PROMISE实例,则新实例的最后结果直接影响了P2的结果
let p2 = p1.then(result => {
// 当PROMISE实例状态为成功,执行THEN存放的第一个函数;RESULT是[[PromiseValue]]
return 10;
}, reason => {
// 当PROMISE实例状态为失败,执行THEN存放的第二个函数;
return Promise.resolve('OK');
});
let p3 = p2.then(result => {}, reason => {}); */
//=>>> p3.then(null,reason => {})
// p3.catch(reason => {});catch方法相当于then里第一个方法不传
Promise.resolve("OK").then(result => {
console.log('成功:' + result);
return 1;
}, reason => {
console.log('失败:' + result);
return 0;
} ).then( result => {
console.log('成功:' + result);
}, reason => {
console.log('失败:' + reason);
});
//成功:OK
//成功:1
Promise.resolve("OK").then(result => {
console.log('成功:' + result);
throw new Error('手动异常')
return 1;
}, reason => {
console.log('失败:' + result);
return 0;
} ).then( result => {
console.log('成功:' + result);
}, reason => {
console.log('失败:' + reason);
});
//成功:Ok
//失败:Error:手动异常
Promise.reject("NO").then(result => {
console.log('成功:' + result);
return 1;
}, reason => {
console.log('失败:' + result);
return 0;
} ).then( result => {
console.log('成功:' + result);
}, reason => {
console.log('失败:' + reason);
});
//失败:NO
//成功:0
// 如果THEN中的某个方法没有写,则顺延至下一个TEHN的指定方法中
//=>reason 某个方法没写,相当于默认加了这个=> {return Promise.reject(reason):};
//=>如果then没写,也是顺延
Promise.reject('NO').then(result => {
console.log('成功:' + result);
return 1;
}, /* reason => {
return Promise.reject(reason);某个方法没写,相当于默认加了这个
}*/).then(result => {
console.log('成功:' + result);
}, reason => {
console.log('失败:' + reason);
});
//失败:NO
//=>如果then没写,也是顺延
Promise.reject('NO').then(result => {
console.log('成功:' + result);
return 1;
}, /* reason => {
return Promise.reject(reason);某个方法没写,相当于默认加了这个
}*/)./*then(result => {
return Promise.resolve(result)
}, */reason => {
console.log('失败:' + reason);
});
//.catch相当于第一个方法没写
Promise.reject('NO').then(result => {
}).catch(reason => {
}).then(result=>{
});
//总结
/*
new promise的时候会把executor函数执行,而exectutor不管你有没有异步,你执行resolve相当于让当前实例变成成功,传值是多少,value值就是多少,执行reject相当于让当前值变成失败,传值是多少,value值就是多少。而你把当前实例变成失败还是成功直接影响了它通过.then存放的哪个方法执行,如果是成功就通知第一个方法执行,如果是失败就通知第二个方法执行。第二个特点是每一次执行.THEN会返回一个新的POMISE实例,每一个全新的POMISE实例都有自己的状态和value值,通过.then返回的promise实例是成功还是失败,还是他的Value值是多少完全取决通过.then存放的存放的两个方法,这两个方法由P1的状态决定了哪个执行,哪个不执行。不管P1.THEN中哪个方法执行,只要执行不报错,则P2的状态就是成功,相反只要报错,P2就是失败,并且方法返回的结果就是P2的VALUE值。
*/
问题1:如果服务器返回的异常,那promise走reject吗?还是catch?
服务器返回异常看你怎么做,服务器返回403,你可以让它报错,也可以让它不报错,那得看自己的了,比如在代码执行过程中,发一个ajax请求,服务器返回一个403,如果你非要返回403的时候也执行resolve,那还是成功。如果你说服务器返回200,你也执行reject,那他也一定失败。所以到底服务器返回成功之后,我们走成功的还是失败的完全取决于你自己执行resolve还是reject。我们讲的基础知识是,resolve执行,它就一定成功,reject执行,它就代表失败,剩下的到底想让它变成功还是失败就看你自己的业务逻辑了。
只要执行P1.then中的某个方法报错了,p2这个promise实例状态就是失败,值就是报错原因,就把P2.then中的第二个reason方法执行。