JavaScript 高阶 Promise篇

1、什么是Promise

Promise 是异步编程的一种解决方案,其实是一个构造函数,自己身上有all、reject、resolve这几个方法,原型上有then、catch等方法。(ps:关于原型:JavaScript高级 构造函数与原型篇)

Promise对象有以下两个特点。

(1)对象的状态不受外界影响。Promise对象代表一个异步操作,有三种状态:pending(进行中)、fulfilled(已成功)和rejected(已失败)。只有异步操作的结果,可以决定当前是哪一种状态,任何其他操作都无法改变这个状态。这也是Promise这个名字的由来,它的英语意思就是“承诺”,表示其他手段无法改变。

(2)一旦状态改变,就不会再变,任何时候都可以得到这个结果。Promise对象的状态改变,只有两种可能:从pending变为fulfilled和从pending变为rejected。只要这两种情况发生,状态就凝固了,不会再变了,会一直保持这个结果,这时就称为 resolved(已定型)。如果改变已经发生了,你再对Promise对象添加回调函数,也会立即得到这个结果。这与事件(Event)完全不同,事件的特点是,如果你错过了它,再去监听,是得不到结果的。

Promise功能:避免了回调地狱,把异步代码改成调用起来像同步代码。

        // 语法:
        // Promise————
        // var  p = new Promis(回调函数)

                // 回调函数也有两个参数
                        // resolve ---------坚定
                        // reject-----------拒绝

        var p = new Promise((resolve,reject)=>{
            //默认状态——————pending

            // 调用函数----resolve();
                // 得到
                // 成功状态————fulfilled

            // 调用函数——--reject()
                // 失败状态————rejected  

                // resolve();
        reject();

        })
        console.log(p);


        // 特点:1、转态不受外部影响
             // 2、状态一旦发生改变,将不再变化

Promise的基本用法:

// 默认pending: 初始状态
var p=new Promise(function (resolve,reject) {
    if("操作成功"){
        resolve();//pending-->fulfilled  异步操作成功的回调函数
    }else{
        reject(); //pending-->reject     异步操作失败的回调函数
    }
})
p.then(data => {//在外面调用then处理成功的逻辑
    console.log("处理成功的逻辑");//fulfilled  
}).catch(err=>{//在外面调用catch处理失败的逻辑
    console.log("失败的逻辑");//reject
})
// then方法会在异步成功后调用,catch方法会在异步失败后调用


如果需要连续调用,就要用return

比如:
        p1.then(data1 => {
            console.log(data1);
            return p2
        }).then(data2 => {
            console.log(data2);
            return p3
        }).then(data3 => {
            console.log(data3);
        })

2、Promise方法的使用

2.1、all方法

接收一个Promise实例对象组成的数组,[p1,p2,p3]

只有p1、p2、p3的状态都变成fulfilled,p的状态才会变成fulfilled,此时p1、p2、p3的返回值组成一个数组,传递给p的回调函数。

只要p1、p2、p3之中有一个被rejected,p的状态就变成rejected,此时第一个被reject的实例的返回值,会传递给p的回调函数。

const p1 = new Promise((resolve, reject) => {
    setTimeout(() => {
        reject("失败");
    }, 3000);
});
const p2 = new Promise((resolve, reject) => {
    setTimeout(() => {
        resolve("成功2");
    }, 2000);
});
const p3 = new Promise((resolve, reject) => {
    setTimeout(() => {
        resolve("成功3");
    }, 1000);
});

// 全部成功返回成功,有一个失败返回失败
let p = Promise.all([p1, p2, p3]).then((res) => console.log(res)).catch(err=>console.log(err));

2.2、allSettled方法

接收一个Promise实例对象组成的数组,[p1,p2,p3]

返回是一个promise,then回调函数中得到每一个promise的详细结果,无论该promise是成功还是失败

      const p1 = new Promise((resolve, reject) => {
        setTimeout(() => {
          reject('ok1')
        }, 3000)
      })

      const p2 = new Promise((resolve, reject) => {
        setTimeout(() => {
          //resolve('ok2')
          //reject('出错啦')
        }, 1000)
      })

      const p3 = new Promise((resolve, reject) => {
        setTimeout(() => {
          reject('ok3')
        }, 1000)
      })
      Promise.allSettled([p1, p2, p3]).then((res) => {
      	console.log(res)
      }).catch((err) => {
         console.log(err)
      })

2.3、any方法

接收一个Promise实例对象组成的数组,[p1,p2,p3]
只要有一个成功的promise对象,就返回这个成功的Promise

      const p1 = new Promise((resolve, reject) => {
        setTimeout(() => {
          reject('ok1')
        }, 3000)
      })

      const p2 = new Promise((resolve, reject) => {
        setTimeout(() => {
          //resolve('ok2')
          //reject('出错啦')
        }, 1000)
      })

      const p3 = new Promise((resolve, reject) => {
        setTimeout(() => {
          reject('ok3')
        }, 1000)
      })
      Promise.any([p1, p2, p3])
        .then((res) => {
          console.log(res) 
        })
        .catch((err) => {
          console.log(err)
        })

2.4、race方法

all是等所有的异步操作都执行完了再执行then方法,那么race方法就是相反的,谁先执行完成就先执行回调。先执行完的不管是进行了race的成功回调还是失败回调,其余的将不会再进入race的任何回调

 
function promiseClick1(){
		let p = new Promise(function(resolve, reject){
			setTimeout(function(){
				var num = Math.ceil(Math.random()*20); //生成1-10的随机数
				console.log('2s随机数生成的值:',num)
				if(num<=10){
					resolve(num);
				}
				else{
					reject('2s数字太于10了即将执行失败回调');
				}
			}, 2000);
		   })
		   return p
	   }
	   function promiseClick2(){
		let p = new Promise(function(resolve, reject){
			setTimeout(function(){
				var num = Math.ceil(Math.random()*20); //生成1-10的随机数
				console.log('3s随机数生成的值:',num)
				if(num<=10){
					resolve(num);
				}
				else{
					reject('3s数字太于10了即将执行失败回调');
				}
			}, 3000);
		   })
		   return p
	   }
	   function promiseClick3(){
		let p = new Promise(function(resolve, reject){
			setTimeout(function(){
				var num = Math.ceil(Math.random()*20); //生成1-10的随机数
				console.log('4s随机数生成的值:',num)
				if(num<=10){
					resolve(num);
				}
				else{
					reject('4s数字太于10了即将执行失败回调');
				}
			}, 4000);
		   })
		   return p
	   }
 
	Promise
		.race([promiseClick3(), promiseClick2(), promiseClick1()])
		.then(function(results){
			console.log('成功',results);
		},function(reason){
			console.log('失败',reason);
		});

2.5、catch方法

与Promise对象方法then方法并行的一个方法就是catch,与try catch类似,catch就是用来捕获异常的,也就是和then方法中接受的第二参数rejected的回调是一样的,如下:

function promiseClick(){
		let p = new Promise(function(resolve, reject){
			setTimeout(function(){
				var num = Math.ceil(Math.random()*20); //生成1-10的随机数
				console.log('随机数生成的值:',num)
				if(num<=10){
					resolve(num);
				}
				else{
					reject('数字太于10了即将执行失败回调');
				}
			}, 2000);
		   })
		   return p
	   }
 
	promiseClick().then(
		function(data){
			console.log('resolved成功回调');
			console.log('成功回调接受的值:',data);
		}
	)
	.catch(function(reason, data){
		console.log('catch到rejected失败回调');
		console.log('catch失败执行回调抛出失败原因:',reason);
	});	

2.7、resolve方法与reject方法

resolve返回一个成功的promise
reject返回一个失败的promise

function promiseClick(){
		let p = new Promise(function(resolve, reject){
			setTimeout(function(){
				var num = Math.ceil(Math.random()*20); //生成1-10的随机数
				console.log('随机数生成的值:',num)
				if(num<=10){
					resolve(num);
				}
				else{
					reject('数字太于10了即将执行失败回调');
				}
			}, 2000);
		   })
		   return p
	   }
 
	promiseClick().then(
		function(data){
			console.log('resolved成功回调');
			console.log('成功回调接受的值:',data);
		}, 
		function(reason){
			console.log('rejected失败回调');
			console.log('失败执行回调抛出失败原因:',reason);
		}
	);	

你可能感兴趣的:(javascript,开发语言,ecmascript)