成人国产在线小视频_日韩寡妇人妻调教在线播放_色成人www永久在线观看_2018国产精品久久_亚洲欧美高清在线30p_亚洲少妇综合一区_黄色在线播放国产_亚洲另类技巧小说校园_国产主播xx日韩_a级毛片在线免费

資訊專欄INFORMATION COLUMN

通過回調(diào)來理解Promise

DevYK / 2410人閱讀

摘要:可信任性確定性在解決上述的回調(diào)函數(shù)的問題之前,有必要先來認識一下的一些主要方法的起點執(zhí)行結(jié)果依次是,,,代碼解讀以上代碼體現(xiàn)了的如下特性一旦決議調(diào)用過一次或者就不再重復(fù)調(diào)用決議回調(diào)或者改變決議回調(diào)。

通過回調(diào)來理解Promise

我們都知道Promise的出現(xiàn)是為了規(guī)避回調(diào)地獄的,由此,我們先來深入了解一下回調(diào)的缺陷:

回調(diào)

1、缺乏信任

2、不確定性

Example

var money = 30;
order(money,function getOrder(orderId){  // order是一個第三方的下訂單的回調(diào)函數(shù)
   orderId && pay(orderId);  // 獲取訂單編號之后調(diào)用第三方支付pay方法去付款 
})
// ...同步代碼

代碼解讀:上面的代碼只是常規(guī)代碼中的一部分,其中order是一個第三方下訂單的方法,需要攜帶回調(diào)函數(shù)過去獲取訂單編號,這里面就存在一些信任性和不確定性的問題,如:

1、有可能回調(diào)函數(shù)getOrder始終不會被調(diào)用,那我們就永遠拿不到訂單編號去支付;
2、有可能回調(diào)了,可是回調(diào)了不止一次,導(dǎo)致我們重復(fù)去支付了;
3、不確定回掉時間,有可能立馬回調(diào),那么接下來的同步代碼就會在回調(diào)之后執(zhí)行,有可能它內(nèi)部調(diào)用了異步代碼再回調(diào),那么接下來的同步代碼就會在回調(diào)之前執(zhí)行。
4、也有可能下訂單的第三方模塊自己內(nèi)部出錯了,導(dǎo)致我們沒辦法捕獲異常;

上面只是回調(diào)的一部分缺陷,但其實當(dāng)我們不喜歡一個東西的時候總有這么多理由,當(dāng)我們喜歡一個東西的時候,沒有理由也會找一堆理由的,下面就是Promise的理由。

Promise

1、可信任性
2、確定性

在解決上述的回調(diào)函數(shù)的問題之前,有必要先來認識一下Promise的一些主要方法:

1、Promise的起點new Promise()

Example

console.log(1);
let promise = new Promise(function PromiseBack(resolve,reject){
    resolve();
    resolve();
    reject();
    reject();
    console.log(2);
}).then(()=>{
    console.log(4);
},()=>{
    console.log(5);
})
console.log(3);
// 執(zhí)行結(jié)果依次是:1,2,3,4

代碼解讀:以上代碼體現(xiàn)了new Promise的如下特性:

1、一旦決議(調(diào)用過一次resolve或者reject)就不再重復(fù)調(diào)用決議回調(diào)或者改變決議回調(diào)。

2、決議代碼是同步的,可是決議的成功或失敗的回調(diào)代碼一定是異步的,而且Promise的異步實現(xiàn)比setTimeout的調(diào)用時間更早,因為回調(diào)決議存在于Event loop的microtask隊列中。

2、多Promise同時執(zhí)行:Promise.all([ .. ])

Example

let promise1 = new Promise(function(resolve,reject){
    resolve(1);
});
let promise2 = new Promise(function(resolve,reject){
    resolve(2);
    // reject(3);
});
let promise3 = Promise.all([promise1,promise2]).then(function resolveBack(result){
    console.log(result);    // 打印結(jié)果是:[ 1, 2 ]
},function rejectBack(result){
    console.log(result);    // 當(dāng)promise2注釋部分放開,非注釋部分注釋,打印結(jié)果是:3
})

代碼解讀:Promise.all方法對于promise數(shù)組的決議是:當(dāng)其中所有的promise都是成功決議的時候,就會調(diào)用成功的決議回調(diào)resolveBack,并且把promise數(shù)組的決議值以數(shù)組的形式按照順序返回resolve中的值;如果其中哪怕有一個失敗的決議都會調(diào)用失敗的決議回調(diào)rejectBack,并且只返回promise宿主中失敗的決議值,以數(shù)組順序返回。

3、多Promise競賽執(zhí)行:Promise.race([ .. ])

Example

let promise1 = new Promise(function(resolve,reject){
  setTimeout(function(){
    resolve(1);
  },100);
});
let promise2 = new Promise(function(resolve,reject){
  setTimeout(function(){
   //resolve(2);
    reject(3);
  },50);
});
let promise3 = Promise.race([promise1,promise2]).then(function resolveBack(result){
    console.log(result);    // 打印結(jié)果是:2
},function rejectBack(result){
    console.log(result);    // 當(dāng)promise2注釋部分放開,非注釋部分注釋,打印結(jié)果是:3
})

代碼解讀:Promise.race方法和all方法不同,它對于promise數(shù)組的決議是:當(dāng)promise數(shù)組中有一個成功了,那就會立即執(zhí)行成功的決議回調(diào),當(dāng)有一個失敗了,就會立即執(zhí)行失敗的決議回調(diào),所以,它也叫競賽決議,它的一個常用的應(yīng)用場景就是異步請求超時處理,代碼如下:
Example:

// request(..)是一個支持Promise的Ajax工具
let promise1 = request( "http://some.url.1/");
let promise2 = function(second=1000){
  return new Promise((resolve,reject)=>{
    setTimeout(()=>{
      reject("請求超時");
    },second)
  })
};
let promise3 = Promise.race([promise1,promise2(3000)])
.then(function resolveBack(result){
    console.log(result);
},function rejectBack(result){
    console.log(result);    // 當(dāng)請求超時3秒鐘就決議失敗,打印錯誤信息,如果這里信息是統(tǒng)一處理,那最好超時的值構(gòu)造成和異步請求返回錯誤結(jié)果的值一致
})
4、Promise錯誤處理catch...

Example

new Promise((resolve,reject)=>{
  console.log(a);
}).catch((err)=>{
  console.log(err);     // 打印結(jié)果:33 [ReferenceError: a is not defined]
})

代碼解讀:catch和then一樣都是Promise的實例方法,而且也都調(diào)用完成之后也都會返回一個新的Promise實例,這樣就可以繼續(xù)then或catch了,這也就是Promise的“鏈?zhǔn)搅鳌?/strong>。其實catch本身實現(xiàn)和then是類似的,可以完全看成是then僅有失敗決議回調(diào),即:then(null,(err)=>{})。也就是說then的失敗決議當(dāng)Promise決議代碼出錯了,哪怕沒有調(diào)用reject方法,也是會被捕獲到錯誤的。

總結(jié)

瀏覽過上述方法之后,我們現(xiàn)在來解決一開始我們遇到的那個回調(diào)函數(shù)的問題,解決問題代碼如下:

Example

var money = 30;
let promise1 = new Promise(function(resolve,reject){
    order(money,function getOrder(orderId){ 
        orderId ? resolve(orderId) : reject(orderId);
    }); 
});
let promise2 = function(second=1000){
  return new Promise((resolve,reject)=>{
    setTimeout(()=>{
      reject("請求超時");
    },second)
  })
};
let promise3 = Promise.race([promise1,promise2(3000)])
.then(function resolveBack(result){
    console.log(result);
},function rejectBack(result){
    console.log(result);    // 當(dāng)請求超時,或者order內(nèi)部代碼錯誤等都會調(diào)用失敗的決議
})
// ...同步代碼

代碼解讀:上面這個Promise例子展示了對回調(diào)問題的規(guī)避,具體解決思路是:

1、通過使用Promise.race競賽決議方法解決如果第三方的order方法不調(diào)用getOrder的情況,可以定位到具體的錯誤代碼和錯誤原因;
2、根據(jù)Promise的決議特性:一旦決議不可狀態(tài)不可更改,不可重復(fù)。解決了回調(diào)了不止一次的問題;
3、根據(jù)Promise的決議回調(diào)是異步的特性,決議的回調(diào)一定是異步的特性,解決了回調(diào)時間的不確定性。
4、根據(jù)rejectBack類似catch的特性,失敗的決議回調(diào)是可以捕獲到?jīng)Q議代碼異常的報錯的,那這樣,如果第三方內(nèi)部出現(xiàn)了問題,是可以捕獲到的。

文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請注明本文地址:http://systransis.cn/yun/84610.html

相關(guān)文章

  • [譯] 深入理解 Promise 五部曲:2. 控制權(quán)轉(zhuǎn)換問題

    摘要:直到最近,我們?nèi)匀辉谟煤唵蔚幕卣{(diào)函數(shù)來處理異步的問題。當(dāng)我們只有一個異步任務(wù)的時候使用回調(diào)函數(shù)看起來還不會有什么問題。 原文地址:http://blog.getify.com/promis... 廈門旅行歸來,繼續(xù)理解Promise 在上一篇深入理解Promise五部曲:1.異步問題中,我們揭示了JS的異步事件輪詢并發(fā)模型并且解釋了多任務(wù)是如何相互穿插使得它們看起來像是同時運行的。...

    alanoddsoff 評論0 收藏0
  • ES6-7

    摘要:的翻譯文檔由的維護很多人說,阮老師已經(jīng)有一本關(guān)于的書了入門,覺得看看這本書就足夠了。前端的異步解決方案之和異步編程模式在前端開發(fā)過程中,顯得越來越重要。為了讓編程更美好,我們就需要引入來降低異步編程的復(fù)雜性。 JavaScript Promise 迷你書(中文版) 超詳細介紹promise的gitbook,看完再不會promise...... 本書的目的是以目前還在制定中的ECMASc...

    mudiyouyou 評論0 收藏0
  • 【譯】理解回調(diào)Promise

    摘要:理解回調(diào)和原文自工程師博客,傳送門這兩個概念是編程語言的基本內(nèi)容?;卣{(diào)地獄就是濫用回調(diào)。通常,在回調(diào)中,錯誤作為第一個參數(shù)傳遞。這個具有這兩個函數(shù)作為參數(shù)的回調(diào)稱為執(zhí)行程序。到目前為止,我希望我已經(jīng)讓自己了解了回調(diào)和。 理解回調(diào)和Promise 原文自工程師Fernando Hernandez博客,傳送門 這兩個概念是Javascript編程語言的基本內(nèi)容。因為這種語言是在異步編程的...

    liuyix 評論0 收藏0
  • 從源碼看 Promise 概念與實現(xiàn)

    摘要:從源碼看概念與實現(xiàn)是異步編程中的重要概念,它較好地解決了異步任務(wù)中回調(diào)嵌套的問題。這些概念中有趣的地方在于,標(biāo)識狀態(tài)的變量如都是形容詞,用于傳入數(shù)據(jù)的接口如與都是動詞,而用于傳入回調(diào)函數(shù)的接口如及則在語義上用于修飾動詞的副詞。 從源碼看 Promise 概念與實現(xiàn) Promise 是 JS 異步編程中的重要概念,它較好地解決了異步任務(wù)中回調(diào)嵌套的問題。在沒有引入新的語言機制的前提下,這...

    kel 評論0 收藏0
  • JavaScript 異步

    摘要:從最開始的到封裝后的都在試圖解決異步編程過程中的問題。為了讓編程更美好,我們就需要引入來降低異步編程的復(fù)雜性。寫一個符合規(guī)范并可配合使用的寫一個符合規(guī)范并可配合使用的理解的工作原理采用回調(diào)函數(shù)來處理異步編程。 JavaScript怎么使用循環(huán)代替(異步)遞歸 問題描述 在開發(fā)過程中,遇到一個需求:在系統(tǒng)初始化時通過http獲取一個第三方服務(wù)器端的列表,第三方服務(wù)器提供了一個接口,可通過...

    tuniutech 評論0 收藏0

發(fā)表評論

0條評論

最新活動
閱讀需要支付1元查看
<