Promise学习笔记

文章介绍了JavaScript中的Promise对象,作为解决回调地狱的方案,详细阐述了Promise的构造函数、链式调用以及状态转变。同时,提到了async函数和await表达式的使用,如何简化异步代码,以及在处理异常和中断Promise链上的应用。
摘要由CSDN通过智能技术生成

Promise

  • 是ES6引入的JS异步编程的解决方案
  • promise是一个构造函数
  • promise对象用来封装一个异步操作,并获取成功或失败的结果值
异步编程(默认使用回调函数)
  • fs文件操作
  • DB操作
  • AJAX
  • 定时器
回调地狱问题(代码不断缩进)【以fs文件操作为例】
const fs = require('fs') //node.js内容
fs.readFile('a.txt',(err,data1)=>{
	if (err1) return "a.txt读取失败";
	//读取a.txt成功后执行
	fs.readFile('b.txt',(err,data2)=>{
		if (err2) return "b.txt读取失败";
		//读取b.txt成功后执行
		fs.readFile('c.txt',(err,data3)=>{
			if (err3) return "c.txt读取失败";
			console.log(data1+data2+data3)
		})
	})
})
promise链式调用解决回调地狱问题【以fs文件操作为例】
const fs = require('fs') //node.js内容
const prm = new Promise((resolve,reject)=>{
	fs.readFile('a.txt',(err,data)=>{
		if(err) reject("a.txt读取失败") //设置promise对象(即prm)的状态为失败
		resolve(data) //设置promise对象(即prm)的状态为成功
	})
})
// promise对象成功后即a.txt读取成功,执行then方法里第一个参数
prm.then(function(value){
	return new Promise((resolve,reject)=>{
		fs.readFile('b.txt',(err,data)=>{
			if(err) reject("b.txt读取失败") //设置promise对象(即prm)的状态为失败
			resolve(data+value) //设置promise对象(即prm)的状态为成功
		})
	})
// promise对象失败后,执行then方法里第二个参数,then方法返回的也是一个Promise对象
},function(reason){
	return reason;
// 即b.txt读取成功
}).then(value=>{
	fs.readFile('c.txt',(err,data)=>{
		if(err) return "c.txt读取失败";
		// c.tx读取成功
		console.log(data+value)
	})
// b.txt读取失败
},reason=>{
	return reason;
})
async函数和await表达式解决地狱回调问题【以fs文件操作为例】
const fs= require('fs')
const util= require('util')
const min= util.promisify(fs.readFile) //传递一个错误优先的回调,返回一个promise的版本

async function fn(){//async函数
	try{
		let data1 = min(a.txt)
		let data2 = min(b.txt)
		let data3 = min(c.txt)
		console.log(data1+data2+data3)
	}catch(e){
		console.log(e) 
	}
} 

Promise语法

promise对象的属性
属性名含义
PromiseState表示promise对象的状态
PromiseResult表示promise对象的值
promise对象的状态『PromiseState』
  • 状态改变:pending–> resolved 调用resolve()
  • 状态改变:pending --> rejected 调用reject() 或 throw ‘111’
  • 一个promise对象状态只能改变一次
new Promise((resolve,reject)=>{
	resolve('222') //输出222,下面的111不会执行不会输出
	reject('111')	
})
  • 成功的数据称为value,失败的数据称为reason
PromiseState属性的值含义
pending未决定的
resolved/fulfilled成功
rejected失败
promise对象的值『PromiseResult』
  • 存储的是异步任务成功或失败的结果
  • resovle()和reject()函数可以修改这个值
promise工作流程

在这里插入图片描述

promise函数
  • Promise()构造函数
  • resolve()函数,在构造函数内部,表示执行成功
  • reject()函数,在构造函数内部,执行失败
// new Promise(executor) executor参数是执行器函数 (resolve,reject)=>{}
new Promise((resolve,reject)=>{
	if (err)reject() //失败
	resolve() //成功
})
  • Promise.prototype.then()方法:then方法返回的也是一个promise对象,所以可以链式调用
  • onResolved函数:成功时调用value=>{}
  • onRejected函数:失败时调用reason=>{}
// p.then(onResolved,onRejected) p是promise对象
p.then(value=>{},reason=>{})
  • Promise.prototype.catch()方法
  • onRejected函数:失败时调用reason=>{}
// p.catch(onRejected) p是promise对象
p.catch(reason=>{})
  • Promise.resolve()方法:属于Promise对象,不属于实例对象
let pr = Promise.resolve(value=>{}) //返回的是一个promise对象

//如果value传递的结果为非promise对象,返回的结果为成功的promise对象
Promise.resolve("111")
//如果value传递的结果为promise对象,则参数的结果决定了resolve的结果
//参数是成功的promise对象,结果就是成功的promise对象,反之亦然
let pr2 = Promise.resolve(new Promise(resolve,reject)=>{resolve("111")}) 
  • Promise.reject()方法:属于Promise对象,不属于实例对象
let pr = Promise.reject(reason=>{}) //返回的是一个失败的promise对象

Promise.reject("111")
//参数是成功的promise对象,结果pr2也是失败的promise对象
let pr2 = Promise.reject(new Promise(resolve,reject)=>{resolve("111")}) 
  • Promise.all()方法:属于Promise对象,不属于实例对象
let pr = Promise.all(promises=>{}) // promises是promise组成的数组,最终结果返回的是一个promise对象

//只有promise数组里所有的Promise对象为成功,结果才为成功。
let pr1 =new Promise((resolve,reject)=>{resolve()})
let pr2 =new Promise((resolve,reject)=>{resolve()})
let pr3 =Promise.all([pr1,pr2])

//如果promise数组里有一个Promise对象为失败,结果为失败。
  • Promise.race()方法:属于Promise对象,不属于实例对象
let pr = Promise.race(promises=>{}) // promises是promise组成的数组,最终结果返回的是一个promise对象

//第一个完成的promise对象的状态,就是最终的返回结果的状态
promise问题
  • 构造函数改变promise状态
    (1)构造函数里调用resolve() 状态是:pending–> resolved
    (2)构造函数里调用reject() 或 throw ‘111’ 状态是:pending --> rejected
  • then函数里改变promise状态
    (1)throw ‘111’ 状态是:pending --> rejected
    (2)then函数里返回值是promise对象以外 状态是:pending–> resolved
    (3)then函数里返回值是promise对象,由promise对象决定。成功就resolved,失败就rejected。
p.then(value=>{
	throw '111' //状态是成功rejected
	return '111' //状态是成功resolved
	return new Promise((resolve,reject)=>{resolve())}) //状态是成功resolved
})
  • 一个promise指定多个回调
let pr1 =new Promise((resolve,reject)=>{
	//resolve()  当是指定了resolve()或者reject() 111和222都会打印出来
	//如果没有指定resolve或reject 当前状态就是pending 所有111和222都不打印出来
	
})
pr1.then(value=>{console.log('111')})
pr1.then(value=>{console.log('222')})
  • 异常穿透:当then链式调用有多个时,不用在中间指定失败的回调,只要在最后指定失败的回调就可以了。
let pr1 =new Promise((resolve,reject)=>{
	reject('aaa')
})
pr1.then(value=>{
	console.log('111')
}).then(value=>{
	console.log('222')
}).catch(reason =>{
	console.log(reason) //输出aaa
})
  • 中断promise链
let pr1 =new Promise((resolve,reject)=>{
	reject('aaa')
})
pr1.then(value=>{
	console.log('111')
	// 有且只有一种方式,就是返回pending状态的promise对象
	return new Promise(()=>{})
}).then(value=>{
	console.log('222')
})then(value=>{
	console.log('333')
})

async 和await

  • async函数和await表达式结合可以让异步代码像同步代码一样

async函数

  • async函数返回结果是promise对象
  • promise对象的结果由async函数执行的返回值决定
//function前面加上async就是 async函数
async function fn(){
	return 'aaa'  //返回值是非promise类型的数据,fn函数返回结果也是promise对象,并且状态是成功的
	throw new Error('aaa') //最终fn函数返回的是失败状态的promise对象
	return new Promise((resolve,reject) => {resolve('成功')}) //返回值是promise对象,最终fn函数返回结果也是promise对象,并且返回值成功fn的primise对象成功状态,失败就失败状态
} 

await表达式

  • await必须写在async函数中
  • await右边也可放一个表达式,一般为promise对象
  • await返回的是promise成功的值
  • 如果表达式是其他值,非promise对象,则直接将此作为await的返回值
  • await的promise失败了,就会抛出异常,需要通过try catch捕获处理
const pm = new Promise((resolve,reject)=>{
	// resolve("aaa")
	// reject("bbb")
})
async function fn(){//async函数
	try{
		let result = await pm;
		console.log(result) //输出promise成功的值,即aaa
		
		let result2 = await 20;
		console.log(result2 )//输出20
	}catch(e){
		console.log(e) //输出promise失败的值,即bbb
	}
	
} 
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值