回调函数使得我们无法使用 return 和 throw 这些关键字的能力, Promise 很好地解决回调地狱的问题。
Promise对象,是一个用来装载异步操作的容器(里面保存着未来才会结束的事件)。
Promise 对象有以下两个特点:
(1)对象的状态不受外界影响。
只有异步操作的结果,可以决定当前是哪一种状态,任何其他操作都无法改变这个状态。有三种状态:pending(进行中)、fulfilled(已成功)和rejected(已失败)。
(2)一旦状态改变,就不会再变,任何时候都可以得到这个结果。
Promise对象的状态改变,只有两种可能:从pending变为fulfilled和从pending变为rejected。
Promise的缺点:
首先,无法取消Promise,一旦新建它就会立即执行,无法中途取消。
其次,如果不设置回调函数,Promise内部抛出的错误,不会反应到外部。
第三,当处于pending状态时,无法得知目前进展到哪一个阶段(刚刚开始还是即将完成)。
1、解决回调地狱问题:
-
当有多个异步请求,且之间有相互依赖关系时,后一个请求需要上一次请求返回的结果,之前我们都会在回调函数里进行嵌套,可读性和可维护性都会很差。
-
使用promise我们就可以用同步操作.then()返回异步操作的结果
2、更好地进行错误捕获:
-
多层回调函数嵌套,可能会造成无法捕获异常或异常捕获不可控。
-
使用promise,通过reject方法,在 catch 方法我们就可以捕捉到。
promise从函数的嵌套改成了链式调用,没有从根本上解决代码的冗杂。
async函数是对 Generator 函数的改进。
async函数自带执行器,async函数的执行,与普通函数一模一样。async表示函数里有异步操作,异步函数也就意味着该函数的执行不会阻塞后面代码的执行,返回值是 Promise 对象。
await命令后面可以放任何表达式,不过我们更多的是放一个返回promise 对象,注意await 关键字只能放到async函数里面。运行结果可能是rejected,所以最好把await命令放在try...catch代码块中。
当函数执行的时候,一旦遇到await就会先返回,等到异步操作完成,再接着执行函数体内后面的语句。其实就是一个一个的yield执行,而且必须一个执行完,才执行下一个。
比如有组数据是很多页面都要用的,我想把它写在一个js文件里作为公共方法。
import axios from 'axios';
axios.defaults.headers.post['Content-Type'] = 'application/x-www-form-urlencoded';
import { get_industrylist } from './api.js'
export const getIndustryList = async function () {
let data = await new Promise((resolve)=>{
axios.post(get_industrylist).then((res) => {
console.log(res)
if(res.data.code === 200){
// console.log('getIndustryList', res.data.data.industrylist)
resolve(res.data.data.industrylist)
}
})
})
return data
}
然后在某个页面里使用它。
created(){
3 getIndustryList().then((v)=>{
4 this.options = v
5 })
6 }
js执行顺序
Promise 构造函数是同步执行的,promise.then 中的函数是异步执行的。