摘要:是異步編程的另一種解決方案函數(shù)是對函數(shù)的改進的基本用法函數(shù)函數(shù)返回一個實例,可以使用方法為返回的實例添加回調(diào)函數(shù)。函數(shù)內(nèi)部語句返回的值,會成為方法回調(diào)函數(shù)的參數(shù)。也就是說,只有函數(shù)內(nèi)部的異步操作執(zhí)行完,才會執(zhí)行方法指定的回調(diào)函數(shù)。
async await
async await是異步編程的另一種解決方案
async函數(shù)是對Generator函數(shù)的改進
async的基本用法 async函數(shù)async函數(shù)返回一個 Promise 實例,可以使用then方法(為返回的Promise實例)添加回調(diào)函數(shù)。當函數(shù)執(zhí)行的時候,一旦遇到await就會先返回,等到異步操作完成,再接著執(zhí)行函數(shù)體內(nèi)后面的語句。
例 1:
上面代碼是一個獲取股票報價的函數(shù),函數(shù)前面的async關(guān)鍵字,表明該函數(shù)內(nèi)部有異步操作。調(diào)用該函數(shù)時,會立即返回一個Promise實例。
async函數(shù)內(nèi)部return語句返回的值,會成為then方法回調(diào)函數(shù)的參數(shù)。
Promise對象的狀態(tài)變化async函數(shù)返回的 Promise對象,必須等到內(nèi)部所有await命令后面的 Promise 對象執(zhí)行完,才會發(fā)生狀態(tài)改變,除非遇到return語句或者拋出錯誤。也就是說,只有async函數(shù)內(nèi)部的異步操作執(zhí)行完,才會執(zhí)行then方法指定的回調(diào)函數(shù)。
await命令的基本用法正常情況下,await命令后面是一個Promise實例,如果不是,會被轉(zhuǎn)成一個立即resolve的Promise實例。
async function f() { return await 123; } f().then(v => console.log(v))
等價于
async function f() { return await new Promise(function(resolve){ resolve(123) }) } f().then(v => console.log(v))
等價于
async function f() { return await Promise.resolve("123") } f().then(v => console.log(v))
await語句的返回值是await命令后面Promise實例的結(jié)果(異步處理的結(jié)果)
function getResult() { return new Promise((resolve) => { resolve("result: 1000") // resolve()方法的參數(shù)就是異步處理的結(jié)果 }); } async function asyncPrint() { const result = await getResult() // 將異步處理的結(jié)果賦值給result return result } asyncPrint().then( (result) => { console.log(result) } ) //"result: 1000"異常處理
如果await后面的異步操作出錯,那么等同于async函數(shù)返回的 Promise 對象被reject。
async function f() { await new Promise(function (resolve, reject) { throw new Error("出錯了"); }); } f() .then(v => console.log(v)) .catch(e => console.log(e)) // Error:出錯了
防止出錯的方法,也是將其放在try...catch代碼塊之中。
async function f() { try { await new Promise(function (resolve, reject) { throw new Error("出錯了"); }); } catch(e) { } return await("hello world"); }使用注意
如果await后面的異步操作出錯,那么等同于async函數(shù)返回的 Promise 對象被reject,所以最好把await命令放在try...catch代碼塊中。
async function myFunction() { try { await somethingThatReturnsAPromise(); } catch (err) { console.log(err); } } // 另一種寫法 async function myFunction() { await somethingThatReturnsAPromise() .catch(function (err) { console.log(err); }); }
多個await命令后面的異步操作,如果不存在繼發(fā)關(guān)系,最好讓它們同時觸發(fā)。
let foo = await getFoo(); let bar = await getBar();
上面代碼中,getFoo和getBar是兩個獨立的異步操作(即互不依賴),被寫成繼發(fā)關(guān)系(只有執(zhí)行完getFoo操作,才能去執(zhí)行g(shù)etBar操作)。這樣比較耗時,因為只有getFoo完成以后,才會執(zhí)行getBar,完全可以讓它們同時觸發(fā)。
解釋:這里的getFoo和getBar方法會返回兩個Promise實例(假設(shè)是發(fā)起Ajax請求,請求foo和bar的內(nèi)容),只有執(zhí)行了方法,對應(yīng)的操作才會執(zhí)行,如果寫成上面的形式,就會導(dǎo)致執(zhí)行完getFoo的操作后(等待收到服務(wù)器的響應(yīng)后),才能執(zhí)行getBar的操作,這樣就成了同步,比較耗時,因此可以將上面的寫法修改,使得在等待getFoo執(zhí)行完的時間內(nèi)(在等待服務(wù)器響應(yīng)的期間)去執(zhí)行執(zhí)行getBar
記住:當函數(shù)執(zhí)行的時候,一旦遇到await就會先返回,等到異步操作完成,再接著執(zhí)行函數(shù)體內(nèi)后面的語句。
// 寫法一 let [foo, bar] = await Promise.all([getFoo(), getBar()]); // 寫法二 let fooPromise = getFoo(); let barPromise = getBar(); let foo = await fooPromise; let bar = await barPromise;
上面兩種寫法,getFoo和getBar都是同時觸發(fā),這樣就會縮短程序的執(zhí)行時間。
參考資料ECMAScript 6 入門
文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。
轉(zhuǎn)載請注明本文地址:http://specialneedsforspecialkids.com/yun/83786.html
摘要:異步操作成果異步操作失敗方法可以接受兩個回調(diào)函數(shù)作為參數(shù)。第一個回調(diào)函數(shù)完成以后,會將返回結(jié)果作為參數(shù),傳入第二個回調(diào)函數(shù)。等同于等同于這段代碼會讓這個對象立即進入狀態(tài),并將錯誤對象傳遞給指定的回調(diào)函數(shù)。 1.Promise的含義 Promise是異步編程的一種解決方案 Promise實例代表一個異步操作,從它可以獲取異步操作的消息 Promise實例有三種狀態(tài): Pending...
摘要:匿名函數(shù)是我們喜歡的一個重要原因,也是,它們分別消除了很多代碼細節(jié)上需要命名變量名或函數(shù)名的需要。這個匿名函數(shù)內(nèi),有更多的操作,根據(jù)的結(jié)果針對目錄和文件做了不同處理,而且有遞歸。 能和微博上的 @響馬 (fibjs作者)掰扯這個問題是我的榮幸。 事情緣起于知乎上的一個熱貼,諸神都發(fā)表了意見: https://www.zhihu.com/questio... 這一篇不是要說明白什么是as...
摘要:整個事件循環(huán)是在一個線程里面的,意味著任務(wù)切換更加高效,無需上下文轉(zhuǎn)換。異步代碼很高效,但是也有很蛋疼的地方,那就是測試。所以我們得想辦法告訴使用一個來運行測試方法。視頻原文:Strategies for testing Async code - PyCon 2019 同時參考了: Testing Asyncio Python Code with Pytest 前面幾篇關(guān)于異步編程的文章...
摘要:因為瀏覽器環(huán)境里是單線程的,所以異步編程在前端領(lǐng)域尤為重要。除此之外,它還有兩個特性,使它可以作為異步編程的完整解決方案函數(shù)體內(nèi)外的數(shù)據(jù)交換和錯誤處理機制。 showImg(https://segmentfault.com/img/bVz9Cy); 在我們?nèi)粘>幋a中,需要異步的場景很多,比如讀取文件內(nèi)容、獲取遠程數(shù)據(jù)、發(fā)送數(shù)據(jù)到服務(wù)端等。因為瀏覽器環(huán)境里Javascript是單線程的,...
摘要:的翻譯文檔由的維護很多人說,阮老師已經(jīng)有一本關(guān)于的書了入門,覺得看看這本書就足夠了。前端的異步解決方案之和異步編程模式在前端開發(fā)過程中,顯得越來越重要。為了讓編程更美好,我們就需要引入來降低異步編程的復(fù)雜性。 JavaScript Promise 迷你書(中文版) 超詳細介紹promise的gitbook,看完再不會promise...... 本書的目的是以目前還在制定中的ECMASc...
閱讀 1633·2021-09-02 15:11
閱讀 1972·2019-08-30 14:04
閱讀 2558·2019-08-27 10:52
閱讀 1574·2019-08-26 11:52
閱讀 1196·2019-08-23 15:26
閱讀 2614·2019-08-23 15:09
閱讀 2603·2019-08-23 12:07
閱讀 2232·2019-08-22 18:41