用Promise控制異步流程,三個異步任務,時間可能有前後,可是要按照想要的順序輸出。
我這裏用四種方法解決,其實也就是考察你對Promise的理解,基礎題了。ajax
//實現mergePromise函數,把傳進去的數組順序前後執行, //而且把返回的數據前後放到數組data中 const timeout = ms => new Promise((resolve, reject) => { setTimeout(() => { resolve(); }, ms); }); const ajax1 = () => timeout(2000).then(() => { console.log('1'); return 1; }); const ajax2 = () => timeout(1000).then(() => { console.log('2'); return 2; }); const ajax3 = () => timeout(2000).then(() => { console.log('3'); return 3; }); function mergePromise(ajaxArray) { //todo 補全函數 } mergePromise([ajax1, ajax2, ajax3]).then(data => { console.log('done'); console.log(data); // data 爲 [1, 2, 3] }); // 分別輸出 // 1 // 2 // 3 // done // [1, 2, 3]
也就是補全上面的mergePromise函數,獲得如上的輸出。數組
function mergePromise(ajaxArray) { let arr = []; async function run() { for(let ifun of ajaxArray) { let cur = await ifun(); arr.push(cur); } return arr; } return run(); }
function mergePromise(ajaxArray){ let arr = []; let p = Promise.resolve(); ajaxArray.forEach(item=>{ p = p.then(data=>{ console.log(data); if(data){ arr.push(data); } return item(); }); }) return p.then(data=>{ arr.push(data); return arr; }) }
先加一層完成狀態的promise(即Promise.resolve()),而後構造一層then鏈,注意第一層是沒有data的,第一次返回的是item(),也就是ajax1(),返回了1,下一步纔有data,即data是1,最後一個item()就是ajax3(),調用並return,咱們要額外在外面用then接受上一步狀態改變的結果也就是上一步return的3(promise中直接return的話是返回resolve的狀態)最後返回arr,讓mergerPromise接受便可。promise
let timeout = function (num, ms) { return new Promise(function (resolve,reject) { setTimeout(() => { resolve(num); }, ms) }); } let timeout1 = timeout(1, 500); let timeout2 = timeout(2, 2000); let timeout3 = timeout(3, 1000); let myPromise = new Promise(function (resolve,reject) { let arr = []; let timeouts = [timeout1,timeout2,timeout3]; runIndex(0); function runIndex(index){ timeouts[index].then(data=>{ console.log(data) arr.push(data); if(index<timeouts.length-1) { console.log('index',index); index++; runIndex(index); }else { resolve(arr); } }) } }); myPromise.then(data => { console.log(data); console.log("done!"); })
我以爲遞歸作這題就是一種bug的作法,徹底就是利用了遞歸的域環境的改變。異步
4.最暴力的直接手寫鏈async
function mergePromise(ajaxArray) { let arr = []; // ajaxArray[0](); return ajaxArray[0]().then(data=>{ arr.push(data); return ajaxArray[1](); }).then(data=>{ arr.push(data); return ajaxArray[2](); }).then(data=>{ arr.push(data); return arr; }) }
也就是上個循環那個展開的樣子,好處就是不用加一層resolve的殼。函數
到此結束,各位有啥意見能夠留個言。code