for循環中接口調用


起因:同事發現一個外層數組為0,但長度為2,這種“奇怪”的數據結構

 

正確的數據結構

 

 

 原因:循環中執行異步請求導致的

 復現業務代碼:

  
//模擬ajax請求
function ajax(){ let data = [{name:'小明',age:22},{name:'小紅',age:18}] return new Promise((resolve,reject)=>{ setTimeout(()=>{ resolve(data) },200) }) } //因業務要求,循環中調用接口 function run(){ let userList = [{id:1},{id:2}]; let list = []; userList.forEach((item)=>{ ajax().then((res)=>{ list.push(res) }) }) console.log(list) } run()

解決方式一 :Promise.all

  function ajax() {
    let data = [{ name: '小明', age: 22 }, { name: '小紅', age: 18 }]
    return new Promise((resolve, reject) => {
      setTimeout(() => {
        resolve(data)
      }, 200)
    })
  }
  創建Promise方法
  function createPromise() {
    let promise = new Promise((resolve, reject) => {
    //將業務接口的返回值,resolve進去 ajax().then((res)
=> { resolve(res) }) }) return promise } function run() { let userList = [{ id: 1 }, { id: 2 }]; let list = []; let resList = []; userList.forEach((item) => { list.push(createPromise()) }) Promise.all(list).then((res) => { resList = res }) } run()

缺點:

   1.Promise.all得等所有請求成功,才能返回,會遇到阻塞問題

   2.Promise.all得等所有請求響應,響應時間太長問題

解決方式二 :遞歸調用接口

  function ajax() {
    let data = [{ name: '小明', age: 22 }, { name: '小紅', age: 18 }]
    return new Promise((resolve, reject) => {
      setTimeout(() => {
        resolve(data)
      }, 200)
    })
  }
 遞歸終止條件,數組長度小於 async
function run(length, arr) { const res = await ajax(); arr.push(res) if (length> 1) { await run(length- 1, arr) } return arr } async function getResult() { let userList = [{ id: 1 }, { id: 2 }]; let res = await run(userList.length, []); } getResult()

優點:恰恰解決了Promise.all的痛點

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM