1.预备工作:
首先定义getData()函数,请求后台的数据(随机卡1~4秒后返回),这个request是axios封装,返回一个Promise变量
由于有axios,这个函数显然是异步的,其实也不用管,只要知道这个是异步请求函数就行了
import request from '@/utils/request'
export function getData(x) {
const data = {
x:x
}
return request({
url: '/getData',
method: 'post',
data: data,
})
}
然后我们的xxx.vue是这样的,点击按钮触发f1(),逻辑容易理解
<template>
<div class="test">
<el-button @click="f1()">获取数据</el-button>
</div>
</template>
<script>
import {getData} from '@/api/testData' //引入外部的getData函数,灵活处理
export default{
data(){
return {
token:getToken(),
Data1:{}
}
}
methods:{
f1(){
//循环多次调用getData(x)
}
}
}
正式开始,我们循环里调用getData()
2.1第一种写法,第一直觉写法
f1(){
//方法1
var dd=[]
for(let i=0;i<5;i++){
var res=getData(i)
let res1=JSON.stringify(res.data.ans)//对象转为json
console.log("res:"+res1)
dd.push(res1)
}
console.log("dd"+dd)
}
输出:
输出循环里并没有得到数据,原因是getData(i)是异步请求,相当于走分叉了,getData()没处理完就console.log输出了
2.2第二种写法 使得循环里输出有数据
由于我们的getData异步返回的是Promise变量,可以加then确保访问后才执行.then后的逻辑
f1(){
//方法2
var dd=[]
for(let i=0;i<5;i++){
getData(i).then((res)=>{
let res1=JSON.stringify(res.data.ans)//对象转为json
dd.push(res1)
console.log("ddli:"+dd)
})
}
console.log("ddwai:"+dd)
}
输出:
分析:
里层的dd有数据了,乱序是因为返回的时间不同,先返回的先push进去了
我们外层的dd没有数据,那是因为输出语句比getData()的循环先执行了
2.3 第三种写法 外层输出也有数据,也就是说等整个循环结束后才往下走
async f1(){
var dd=[]
! await function f2(){
return new Promise(resolve=>{
var cnt=0;
for(let i=0;i<5;i++){
getData(i).then((res)=>{
let res1=JSON.stringify(res.data.ans)//对象转为str
dd.push(res1)
console.log("ddli:"+dd)
cnt++;
if(cnt==5)resolve()
})
}
})
}()
console.log("ddwai:"+dd)
}
输出:
分析:首先我们使用async 与await
async 函数(){} :声明函数里含有异步
await 表达式 等待表达式/包括函数,完成后才往下走,这里我们配合Promise来使用
那么我们的写法就是
await 函数()
{
返回一个Promise对象
return new Promise(
resolve=>{
异步函数().then(
(异步函数返回的结果)=>{
if(满足条件){
resolve()结束Promise
}
}
)
}
)
}
!function f2(){}()
等价于
function f2(){}
f2()
在Promise对象里 当if(满足条件){ resolve(); }来结束Promise 往下走
在这里我们的满足条件就是5个getData()全部完成,因此我们加一个计数器cnt来记录
2.4第四种写法 外层输出有数据,且返回依次按顺序执行(使用递归)
async f1(){
var dd=[]
! await function f2(){
return new Promise(resolve=>{
var x=0;
dfs(x)
function dfs(x){ //递归
getData(x).then((res)=>{
let res1=JSON.stringify(res.data.ans)//对象转为json
dd.push(res1)
console.log("ddli:"+dd)
x++;
if(x<5){
dfs(x)
}else{
resolve()//递归完成,返回Promise.resolve
}
})
}
})
}()
await console.log("ddwai:"+dd)
}
输出:
不仅会按顺序依次返回(解决有依赖的情况),而且外层也有值了