摘要:使用承諾對象使我們有機會將異步操作的最終成功或失敗關聯到功能無論出于何種原因。例如在上面的示例中函數解析為值在成功完成時并在返回值這是另一個承諾上調用函數依此類推等等。這意味著我們只能返回一個承諾一次。
本文轉載自:眾成翻譯
譯者:iOSDevLog
鏈接:http://www.zcfy.cc/article/3814
原文:https://www.fullstackreact.com/30-days-of-react/day-15/
今天,我們將要看看我們需要知道什么來從高層次了解Promises,所以我們可以使用這個非常有用的概念構建我們的應用。
昨天我們將 fetch 庫安裝到我們的 create-react-app 項目 我們開始 第12天. 今天, 我們將拿起從昨天討論的概念和Promises的 藝術 .
Promise正如 mozilla 所定義的, 承諾對象用于處理異步計算, 其中有一些重要的保證難以用回調方法處理 (更老式的處理異步代碼的方法)。
Promise 對象只是圍繞一個值的包裝, 它在實例化對象時可能也可能不知道, 并提供了一個已知的 (也稱為 resolved) 或由于失敗原因而不可用 (我們將此稱為rejected) 后 處理該值的方法 。
使用 "承諾" 對象使我們有機會將異步操作的最終成功或失敗關聯到功能 (無論出于何種原因)。它還允許我們使用類似于同步的代碼來處理這些復雜的場景。
例如, 考慮下面的同步代碼, 我們在 javascript 控制臺中打印出當前時間:
var currentTime = new Date(); console.log("The current time is: " + currentTime);
這是相當直接的, 并作為 new Date() 對象表示瀏覽器知道的時間。現在考慮我們在其他遠程機器上使用不同的時鐘。例如, 如果我們正在做一個快樂的新年時鐘, 這將是偉大的, 能夠同步用戶的瀏覽器與其他人使用一個單一的時間值為每個人, 所以沒有人錯過的落球儀式。。
假設我們有一個方法來處理從遠程服務器獲取當前時間的 getCurrentTime() 時鐘。現在, 我們將用setTimeout() 來表示這一點, 它返回時間 (就像對慢速 api 發出請求一樣):
function getCurrentTime() { // Get the current "global" time from an API return setTimeout(function() { return new Date(); }, 2000); } var currentTime = getCurrentTime() console.log("The current time is: " + currentTime);
我們的console.log() 日志值將返回超時處理程序 id, 這絕對 不是 當前時間。傳統上, 我們可以使用回調來更新代碼, 以便在可用時間時調用:
function getCurrentTime(callback) { // Get the current "global" time from an API return setTimeout(function() { var currentTime = new Date(); callback(currentTime); }, 2000); } getCurrentTime(function(currentTime) { console.log("The current time is: " + currentTime); });
如果有其余的錯誤呢?我們如何捕獲錯誤并定義重試或錯誤狀態?
function getCurrentTime(onSuccess, onFail) { // Get the current "global" time from an API return setTimeout(function() { // randomly decide if the date is retrieved or not var didSucceed = Math.random() >= 0.5; if (didSucceed) { var currentTime = new Date(); onSuccess(currentTime); } else { onFail("Unknown error"); } }, 2000); } getCurrentTime(function(currentTime) { console.log("The current time is: " + currentTime); }, function(error) { console.log("There was an error fetching the time"); });
現在, 如果我們想根據第一個請求的值提出請求怎么辦?作為一個簡短的示例, 讓我們再次重用 getCurrentTime() 函數 (就好像它是第二個方法, 但允許我們避免添加另一個復雜的函數):
function getCurrentTime(onSuccess, onFail) { // Get the current "global" time from an API return setTimeout(function() { // randomly decide if the date is retrieved or not var didSucceed = Math.random() >= 0.5; console.log(didSucceed); if (didSucceed) { var currentTime = new Date(); onSuccess(currentTime); } else { onFail("Unknown error"); } }, 2000); } getCurrentTime(function(currentTime) { getCurrentTime(function(newCurrentTime) { console.log("The real current time is: " + currentTime); }, function(nestedError) { console.log("There was an error fetching the second time"); }) }, function(error) { console.log("There was an error fetching the time"); });
以這種方式處理 異步 會很快變得復雜。此外, 我們可以從以前的函數調用中獲取值, 如果我們只想得到一個... 在處理應用啟動時還沒有的值時, 有很多棘手的情況需要處理。
進入Promise使用承諾, 另一方面幫助我們避免了很多這種復雜性 (雖然不是一個銀彈解決方案,參考《人月神話》)。以前的代碼, 這可以被稱為意大利面條代碼可以變成一個更整潔, 更同步的前瞻版本:
function getCurrentTime(onSuccess, onFail) { // Get the current "global" time from an API using Promise return new Promise((resolve, reject) => { setTimeout(function() { var didSucceed = Math.random() >= 0.5; didSucceed ? resolve(new Date()) : reject("Error"); }, 2000); }) } getCurrentTime() .then(currentTime => getCurrentTime()) .then(currentTime => { console.log("The current time is: " + currentTime); return true; }) .catch(err => console.log("There was an error:" + err))
以前的源代碼示例對正在發生的事情進行了一些清理和清除, 避免了許多棘手的錯誤處理/捕獲。
為了獲得成功的值, 我們將使用Promise 實例對象上的 then() 功能。then() 函數被調用, 無論返回值是Promise本身。例如, 在上面的示例中, getCurrentTime() 函數解析為currentTime() 值 (在成功完成時), 并在返回值 (這是另一個承諾) 上調用then() 函數, 依此類推等等。
要捕獲在承諾鏈中任何地方發生的錯誤, 我們可以使用catch() 方法。
單使用Guarantee我們在上面的例子中使用一個承諾鏈, 以創建一個 鏈 的行動, 被稱為一個接一個。
承諾鏈聽起來很復雜, 但基本上很簡單。實質上, 我們可以連續地 "同步" 調用多個異步操作。對then() 的每次調用都用以前的then() 函數的返回值來調用。
例如, 如果我們想操縱getCurrentTime() 調用的值, 我們可以在鏈中添加一個鏈接, 如下所示:getCurrentTime() .then(currentTime => getCurrentTime()) .then(currentTime => { return "It is now: " + currentTime; }) // this logs: "It is now: [current time]" .then(currentTimeMessage => console.log(currentTimeMessage)) .catch(err => console.log("There was an error:" + err))
承諾在任何特定的時間都只應該在三種狀態之一:
待定
已完成 (已解決)
已拒絕 (錯誤)
一個 待定 的承諾只能導致一個滿足狀態或一個被拒絕的狀態 一次且僅一次 , 這可以避免一些相當復雜的錯誤場景。這意味著, 我們只能返回一個承諾一次。如果我們想重新運行一個使用承諾的函數, 我們需要創建一個 新 的。
創建一個Promise我們可以使用 Promise構造函數來創建新的承諾 (如上面的示例所示)。它接受一個有兩個參數來運行的函數:
onSuccess (or resolve) 函數將在成功解析后被調用
onFail (or reject) 函數在失敗拒絕后被調用
從上面回顧我們的函數, 我們可以看到, 如果請求成功, 我們調用 resolve() 函數, 如果該方法返回錯誤條件, 則調用 reject() 函數。
var promise = new Promise(function(resolve, reject) { // call resolve if the method succeeds resolve(true); }) promise.then(bool => console.log("Bool is true"))
現在我們知道了什么是承諾, 如何使用, 以及如何創建它們, 我們實際上可以使用昨天安裝的 fetch() 庫。
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://specialneedsforspecialkids.com/yun/84683.html
摘要:今天我們將討論創建組件的最終方案,即無狀態函數的純組件。今天我們正在研究一種處理提出的復雜數據的方法,稱為體系結構。第天部署介紹今天,我們將探討部署我們的應用所涉及的不同部分,以便外界可以使用我們的應用。 本文轉載自:眾成翻譯譯者:iOSDevLog鏈接:http://www.zcfy.cc/article/3758原文:https://www.fullstackreact.com/3...
摘要:在方法中處理數據有三不同的角色派發器儲存視圖層我們的組件的主要思想是有一個單一源儲存他們只能通過觸發更新。這些操作負責調用派發器可以訂閱更改并相應地更新自己的數據。與不同不使用派發器而是使用純函數來定義數據變異函數。 本文轉載自:眾成翻譯譯者:iOSDevLog鏈接:http://www.zcfy.cc/article/3812原文:https://www.fullstackreact...
摘要:我們將討論三種不同的軟件測試范例單元測試功能測試和集成測試。在中單元測試通常不需要瀏覽器可以快速運行不需要寫入斷言本身通常是簡單而簡潔的。集成測試最后我們將研究的最后一種測試是集成測試。 本文轉載自:眾成翻譯譯者:iOSDevLog鏈接:http://www.zcfy.cc/article/3809原文:https://www.fullstackreact.com/30-days-of...
摘要:并總結經典面試題集各種算法和插件前端視頻源碼資源于一身的文檔,優化項目,在瀏覽器端的層面上提升速度,幫助初中級前端工程師快速搭建項目。 本文是關注微信小程序的開發和面試問題,由基礎到困難循序漸進,適合面試和開發小程序。并總結vue React html css js 經典面試題 集各種算法和插件、前端視頻源碼資源于一身的文檔,優化項目,在瀏覽器端的層面上提升速度,幫助初中級前端工程師快...
閱讀 870·2021-11-18 10:02
閱讀 1670·2019-08-30 15:56
閱讀 2570·2019-08-30 13:47
閱讀 2639·2019-08-29 12:43
閱讀 851·2019-08-29 11:19
閱讀 1783·2019-08-28 18:23
閱讀 2669·2019-08-26 12:23
閱讀 3007·2019-08-23 15:29