ES6 中使用Promsie解决回调地狱
1,Promsie概念
- Promise 是异步编程的一种解决方案,比传统的回调函数和事件更合理、更强大
- ES6的Promise是一个构造函数, 用来生成Promise实例, Promise实例是异步操作管理者
- Promise代表了未来某个将要发生的事件(通常是一个异步操作) 有了Promise对象
- 可以将异步操作以同步的流程表达出来,避免了层层嵌套的回调函数(回调地狱)
- Promise本身还是在使用回调函数(只不过比回调函数多了一种状态管理)
2,Promsie函数
- Promsie回调内置两个参数 第一个参数是成功状态 第二个参数是失败状态
- 无论是成功装填的resolve 还是失败装填的reject 都是一个函数
- 那么我们成功 就可以调用resolve函数 失败调用reject函数
- Promise 三种状态
- 挂起状态 pending 也叫许诺状态
- 成功状态 fullfilled
- 失败状态 rejected
-
resolve 函数会使promsie状态改为fullfilled 状态
reject 函数会使promsie状态改为rejected 状态
let promise = new Promise((resolve, reject) => {
const isSuccess = true //这里写异步代码 或 请求 - 我这边直接默认请求成功了
// 成功时调用 resolve 函数
if (isSuccess) {
resolve('成功') // 会执行then()方法的第一个回调函数
} else {
// 失败时调用reject 函数
reject('失败') // 会执行then()方法的第二个回调函数
}
})
3,Promise then()方法
- 上面编辑完成Promise 其实才完成一半
- 我们如果说想让这个promise执行的话 那么需要promise对象中的then方法触发
- then方法内置一个或者两个参数
- 第一个参数是回调函数 他是成功状态的执行函数 也就是resolve函数
- 第二个参数也是回调函数 他是失败状态的执行函数 也就是reject函数
-
promise.then(
(data) => {
//data
console.log('我执行成功了:' + data)
},
(err) => {
console.log('我执行失败了:' + err)
}
)
上面是Promsie then方法的调用 【但是注意:当代码报错的时候,会出现错误信息 这时使用then方法无法捕获异常信息】
那么在Promise中也是存在异常处理的 就是catch()方法
所以说 失败状态一般我们不会使用then方法进行触发 then方法只会触发成功状态 catch方法用来处理异常的情况
上面代码改写为一下:
promise
.then((data) => {
console.log('我执行成功了:' + data)
})
.catch((err) => {
console.log('我执行失败了:' + err)
})
4,Promise 链式操作
then方法的第一个参数,成功时的回调函数,分两种情况:
1,返回了一个普通的数据(非promise),这个值会作为参数传递给下一个then的成功回调
2,返回了一个promise,下一个then的执行,取决于这个promise状态的改变
==================下面用 Promsie链式操作解决异步嵌套问题====================
aaa(),bbb(),ccc(),ddd()函数都返回了一个promsie 对象 ,那么就可以使用then()方法进行链式操作,用同步的代码形式执行异步的操作
简单明了,优雅的解决了回调地狱。
aaa()
.then(() => {
return bbb()
})
.then(() => {
return ccc()
})
.then(() => {
ddd()
})
打印的代码执行顺序如下: 非常符合同步的执行逻辑期望
aaa - sleep 2s
bbb - sleep 1s
ccc - sleep 3s
ddd - sleep 1s
====================以下四个函数都是用定时器模拟异步执行的(开发中更多使用的是http请求,是一样的道理)====================
function aaa() {
return new Promise((resolve, reject) => {
setTimeout(() => {
console.log('aaa - sleep 2s')
resolve()
}, 2000)
})
}
function bbb(resolve) {
return new Promise((resolve, reject) => {
setTimeout(() => {
console.log('bbb - sleep 1s')
resolve()
}, 1000)
})
}
function ccc(resolve) {
return new Promise((resolve, reject) => {
setTimeout(() => {
console.log('ccc - sleep 3s')
resolve()
}, 3000)
})
}
function ddd(resolve) {
return new Promise((resolve, reject) => {
setTimeout(() => {
console.log('ddd - sleep 1s')
resolve()
}, 1000)
})
}