摘要:換句話說該靜態函數返回個處于狀態的對象。等價于構造函數的靜態函數,創建一個對象并以值作為參數調用句柄函數。等價于介紹構造函數的靜態函數,參數是對象組成的可迭代數據集合。
一、概述
ES2015 Promise函數是對PromiseA+標準的實現,并且嚴格遵守該標準。
二、APIs 2.1 創建Promise對象Promise構造函數的參數是個包含兩個參數的函數,并且該函數的參數分別對應resolve, reject操作(resolve,reject也是函數)。并且只能通過這兩個參數改變Promise的狀態。
function asynOperation(){ var promise = new Promise(function(resolve, reject){ setTimeout(function(){ reject(1,2,3); // 調用reject操作,并傳遞reason參數。雖然傳遞多個參數,但只把第一個作為reson值,符合Promise A+標準 }, 3000) }); return promise; } asynOperation().then(function(value){ console.log("ES2015 Promise: resolved and value is " + value); }, function(reason){ console.log("ES2015 Promise: rejected and reason is " + reason); })
上面的代碼用zpotojs實現:
/* ZeptoJS Deferred */ function AsynOperation1(){ var deferred = $.Deferred(); setTimeout(function(){ deferred.reject(1, 2, 3); }, 3000); return deferred.promise(); } AsynOperation1().then(function(val){ console.log("Fullfilled: " + val); }, function(reason){ console.log("Rejected: " + reason); })2.2 Promise.prototype.catch
catch方法用來添加Rejected狀態回調,是then方法的一種子集。
asynOperation().catch(function(reason){ }) // 等價于 asynOperation().then(undefined, function(reason){ })2.3 Promise.reject(reason)
Promise構造函數的靜態方法,創建個Promise對象并以reason值調用reject句柄函數。換句話說該靜態函數返回個處于“Rejected”狀態的Promise對象。
var p = Promise.reject(1); // 等價于 var p = new Promise(function(resolve, reject){ reject(1); })2.4 Promise.resolve(value)
Promise構造函數的靜態函數,創建一個Promise對象并以value值作為參數調用resolve句柄函數。換句話說該靜態函數返回個處于“fullfilled"狀態的Promise對象。
var p = Promise.resolve(1); // 等價于 var = new Promise(function(resolve){ resolve(1); })2.5 Promise.all(iterable) 2.5.1 介紹
Promise構造函數的靜態函數,參數是Promise對象組成的可迭代數據集合。創建個Promise對象,并且參數指定的所以Promise都解決后,該Promise對象該被解決,反之如果其中存在rejected的Promise,則該Promise對象被rejected。
定義個異步操作:
function asynOperation(value, reason){ var promise = new Promise(function(resolve, reject){ setTimeout(function(){ value === undefined ? reject(reason) : resolve(value); }, 3000) }); return promise; } var p1 = asynOperation(1), p2 = asynOperation(2), p3 = asynOperation(3); Promise.all([p1, p2, p3]).then(function(value){ console.log("all resolved: value is " + value); // value是[1, 2, 3] })
如果參數元素中發生rejected操作,則立馬reject返回的Promise:
var p1 = asynOperation(1), p2 = asynOperation(undefined, 2), // reject操作 p3 = asynOperation(undefined, 3); // reject操作 p2.catch(function(reson){ console.log("p2") }) p3.catch(function(reson){ console.log("p3") }) Promise.all([p1, p2, p3]).then(function(value){ console.log("all resolved: value is " + value) }, function(reason){ console.log("one rejected: reason is " + reason); // reson值等于發生reject操作的promise對象的reason,即p2 })
顯示結果:
2.5.2 對比$.whenPromise.all和$.when很類似。主題功能差不多,參數傳遞方式不一樣:ES2015中把所有的Promise對象的value構建個數組,而$.when是分別傳遞的。
function AsynOperation1(value, reason){ var deferred = $.Deferred(); setTimeout(function(){ value === undefined ? deferred.reject(reason) : deferred.resolve(value); }, 3000); return deferred.promise(); } var p1 = AsynOperation1(1), p2 = AsynOperation1(2), p3 = AsynOperation1(3); $.when(p1, p2, p3).then(function(value){ console.log("resolved " + value); // 留意Value的值 }, function(reason){ console.log("rejected " + reason); })2.6 Promise.race(iterable)
Promise構造函數的靜態函數,參數是Promise對象構成的可迭代對象,創建個Promise對象。當參數任意Promise對象fullfilled(rejected)時,則立馬fullfill(reject)該Promise對象。
var p1 = asynOperation(1), p2 = asynOperation(undefined, 2), p3 = asynOperation(undefined, 3); Promise.race([p1, p2, p3]).then(function(value){ console.log("one resolved: value is " + value); // Value=1 }, function(reason){ console.log("one rejected: reason is " + reason) })三、micro-task
Promise的回調通過micor-task實現的。
console.log(1) setTimeout(function(){ console.log(2)}, 0) Promise.resolve().then(function(){console.log(3)}) console.log(4) // 輸出應該是:1 4 3 2四、對比Promise A+ 標準
大部分Promise A+標準的實現對"Promise解決過程"標準的實現略有不同,比如zeptoJs Deferred就沒考慮thenable情況。但是ES2015 Promise函數完全嚴格遵守Promise A+標準,包含對“Promise 解決過程的實現。下面舉例說明實現Promise解決過程(The Promise Resolution Procedure):[[Resolve]](promise, x)
3.3.1 如果promise對象和x相等,則用TypeError對象作為reason 拒絕promise對象var p1 = asynOperation(1); var p2 = p1.then(function(value){ console.log("resolved: " + value); return p2; // 返回p2對象, },function(reason){ console.log("rejected: " + reason); }}; }); p2.then(function(value){ console.log("resolved: " + value); },function(reason){ console.log("rejected: " + reason);
var p1 = asynOperation(1); var p2 = p1.then(function(value){ console.log("resolved: " + value); return asynOperation(2); // 返回個Promise對象,以該Prmoise對象狀態決定p2的狀態 },function(reason){ console.log("rejected: " + reason); }); p2.then(function(value){ console.log("resolved: " + value); },function(reason){ console.log("rejected: " + reason); })3.3.3 如果x是thenable,promise狀態的改變取決于x.then方法的執行中resolve,reject句柄的調用情況。并不受x.then返回值的影響。
A:then方法沒有調用resolve或者reject,并且沒有返回值,則不會改變promose的狀態
var p1 = asynOperation(1); var p2 = p1.then(function(value){ console.log("resolved: " + value); return {name: "john", then: function(resolve, reject){ // 返回值是個thenable對象,但是then方法沒有調用resolve或者reject,并且沒有返回值 }}; },function(reason){ console.log("rejected: " + reason); }); p2.then(function(value){ console.log("resolved: " + value); },function(reason){ console.log("rejected: " + reason); })
B:then方法中調用resolve句柄,用新value y遞歸調用Promise解決過程:[[Resolve]](promise, y)
var p1 = asynOperation(1); var p2 = p1.then(function(value){ console.log("resolved: " + value); return {name: "john", then: function(resolve, reject){ resolve(2); // then方法中調用resolve句柄,用新value遞歸調用Promise解決過程 }}; },function(reason){ console.log("rejected: " + reason); }); p2.then(function(value){ console.log("resolved: " + value); },function(reason){ console.log("rejected: " + reason); })
C:then方法中調用reject句柄,則用相同的reason拒絕promise.
var p1 = asynOperation(1); var p2 = p1.then(function(value){ console.log("resolved: " + value); return {name: "john", then: function(resolve, reject){ reject(2); // 調用reject句柄 }}; },function(reason){ console.log("rejected: " + reason); }); p2.then(function(value){ console.log("resolved: " + value); },function(reason){ console.log("rejected: " + reason); })
D:then方法中多次調用resolve, reject句柄,只有第一個調用有效,其他的忽略
E:then方法中拋異常,如果拋異常之前已經調用resolve或者reject句柄,則忽略該異常,反之則以該異常為reason拒絕promise
2.3.4 其他情況,則用x作為value完成promise。var p1 = asynOperation(undefined, 1); // 拒絕的promise var p2 = p1.then(function(value){ console.log("resolved: " + value); return {name: "john"}; },function(reason){ console.log("rejected: " + reason); return 2; }); p2.then(function(value){ console.log("resolved: " + value); },function(reason){ console.log("rejected: " + reason); })還沒結束
一道關于Promise應用的面試題
參考是時候使用promise了
avaScript Promise迷你書(中文版)
MDN
文章版權歸作者所有,未經允許請勿轉載,若此文章存在違規行為,您可以聯系管理員刪除。
轉載請注明本文地址:http://specialneedsforspecialkids.com/yun/93321.html
摘要:的翻譯文檔由的維護很多人說,阮老師已經有一本關于的書了入門,覺得看看這本書就足夠了。前端的異步解決方案之和異步編程模式在前端開發過程中,顯得越來越重要。為了讓編程更美好,我們就需要引入來降低異步編程的復雜性。 JavaScript Promise 迷你書(中文版) 超詳細介紹promise的gitbook,看完再不會promise...... 本書的目的是以目前還在制定中的ECMASc...
摘要:和和都有和,但是略有不同。實際上返回的是一個對象。和添加的回調,添加的回調。所以在調用成功的情況下執行添加的回調,調用失敗時執行添加的回調。,產生對象并,產生對象并,然后繼續處理,的語法糖,和的差不多但不同。 Deferred 和 Promise ES6 和 jQuery 都有 Deffered 和 Promise,但是略有不同。不過它們的作用可以簡單的用兩句話來描述 Deffere...
摘要:所謂異步編程中的異步是相對于同步的概念的。是一系列異步編程規范的統稱。如果中的回調函數返回一個值,那么返回的將會成為接受狀態,并且將返回的值作為接受狀態的回調函數的參數值。參考介紹基礎篇深入理解與異步編程。 es6 promise與異步編程 對于一些還不具備大量編程經驗的朋友來說,promise可能是es6比較難以掌握的點。首先是很多名詞,比如Promises,es6 Promise,...
摘要:從最開始的到封裝后的都在試圖解決異步編程過程中的問題。為了讓編程更美好,我們就需要引入來降低異步編程的復雜性。寫一個符合規范并可配合使用的寫一個符合規范并可配合使用的理解的工作原理采用回調函數來處理異步編程。 JavaScript怎么使用循環代替(異步)遞歸 問題描述 在開發過程中,遇到一個需求:在系統初始化時通過http獲取一個第三方服務器端的列表,第三方服務器提供了一個接口,可通過...
摘要:如果有錯誤,則到的第二個回調函數中,對錯誤進行處理。假設第一個的第一個回調沒有返回一個對象,那么第二個的調用者還是原來的對象,只不過其的值變成了第一個中第一個回調函數的返回值。 ES6標準出爐之前,一個幽靈,回調的幽靈,游蕩在JavaScript世界。 正所謂: 世界本沒有回調,寫的人多了,也就有了})})})})})。 Promise的興起,是因為異步方法調用中,往往會出現回調函數一...
摘要:就算改變已經發生了,即使再對對象添加回調函數,也會立即得到這個結果。方法接收個參數,第一個參數是狀態的回調函數,第二個參數可選是狀態的回調函數。簡單來講,就是能把原來的回調寫法分離出來,在異步操作執行完后,用鏈式調用的方式執行回調函數。 在ECMAScript 6標準中,Promise被正式列為規范,Promise,字面意思就是許諾,承諾,嘿,聽著是不是很浪漫的說?我們來探究一下這個浪...
閱讀 1711·2021-11-11 10:58
閱讀 4186·2021-09-09 09:33
閱讀 1257·2021-08-18 10:23
閱讀 1548·2019-08-30 15:52
閱讀 1625·2019-08-30 11:06
閱讀 1867·2019-08-29 14:03
閱讀 1507·2019-08-26 14:06
閱讀 2943·2019-08-26 10:39