promise解決異步問題:.then和async_await的淵源


1.為什么要使用回調函數?

當我們的請求既有異步,又有同步的時候,如果異步請求在同步請求的上方,異步請求比較慢,要先等待異步請求執行完再去執行同步請求,比較耗時。這時候我們將異步請求放在一個回調函數里,就不必等待異步請求執行完再去執行同步請求。

其實使用回調函數最終目的是為了獲得外層普通函數(同步請求)的執行結果res,使用箭頭函數的最終目的是為了獲得上一個回調函數的執行結果res.

2.為什么使用promise呢?

在一段代碼中,如果有兩個異步請求,例如有兩個回調函數,我們想讓第一個函數(代碼在上方)執行完成之后,得到一個結果,再去執行第二個函數(代碼在下方)

由於異步請求的執行不一定是按照代碼從上到下的順序執行的,因此程序有可能先執行第二個函數,再去執行第一個函數,這樣就會報錯。為了解決這個問題,傳統的方法

是將第二個回調函數嵌套在第一個回調函數內部,就可以保證第一個回調函數執行完成后再執行第二個回調函數。但是問題又來了,如果一段代碼中有多個回調函數,就要不停的嵌套,就會進入回調地獄,這時候promise就派上用場了。

有了 Promise 對象,就可以將異步操作以同步操作的流程表達出來,避免了層層嵌套的回調函數。

promise可以使用.then(res)=>{函數體}的方式,將上一個函數返回結果res作為參數傳遞到下一個回調函數中去,這樣就能保證上一個函數執行完成之后,再執行下一個函數。其中axios就是基於promise的。

qpromise()
.then((res)=>{
//code
return res.a;
})
.then((res)=>{
//code
return res.b;
})
.then((res)=>{
//code
return res.c;
})


采用鏈式寫法,即then后在調用另一個then方法

3.

ES6規定,Promise 對象是一個構造函數,用來生成Promise 實例。

下面的代碼就是一個Promise 實例:

復制代碼
var promise=new Promise(function(resolve,reject){
    //code
    if(/*異步操作*/){
        resolve();
    }else{
        reject();
    }
})

Promise構造函數接受一個函數作為參數,該函數有兩個參數分別是resolve和reject,它們也是函數。

resolve函數的作用是,將Promise 對象的狀態從“未完成”(pending)==>“成功”(resolved),在異步操作成功時調用,並將異步操作結果,作為參數傳遞出去。

reject函數的作用是,將Promise 對象的狀態從“未完成”(pending)==>“失敗”(rejected),再異步操作失敗時調用,並將操作報錯的錯誤,作為參數傳遞出去。

3.緊接着問題又來了,這樣還是會產生很多回調函數,要不停的.then(()=>{ }),現在async和await就派上用場了,它可以讓異步方法執行的順序依據我們的需求而定,兩者是結合使用的,await后面跟的是promise實例,

也就是說,async,await和promise三者必須連用。

例如我們現在有兩個promise實例,

 

 

 

 那么我們會先執行fnPromise1(),再執行fnPromise2(),雖然fnPromise1()是在3秒之后執行,fnPromise2()是在2秒之后執行,按理說應該先執行fnPromise2(),但是由於我們用了await,就相當於同步,先執行第一個await,再執行第二個await. await要放在異步方法里面使用,和promise或者async結合使用。無論是使用箭頭函數,還是使用await,最終結果都是獲得promise.


免責聲明!

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



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