我知道node.js有很多control flow libraries。其中一些使用回調(例如async,asyncblock等)讓一個鏈異步函數,其他使用promise concept(Q,延期,期貨等)。鑑於長時間運行的腳本會一個接一個地執行一系列可能會失敗的操作,您更喜歡哪種控制流程,爲什麼?優缺點都有什麼?Node.js控制流:回調還是承諾?
回答
我不認爲有很多客觀的優點和缺點。異步非常流行(基於npm packages that depend on it)。
我喜歡控制流庫(特別是異步),因爲它更容易理解。承諾混淆了我,而異步很容易理解。我懷疑它只是一個學習曲線的東西,如果我花費精力去學習它,承諾會更具可讀性。但是,我是否應該期望那些試圖閱讀我的代碼的人呢?
還有第三種 - Fibers。 Fibers不能在Windows上工作,但(IMO)爲應該以串行方式執行的事情提供最清晰的語法。
優點回調:
- 簡單理解和創造。
- 有點效率更高,因爲更少的對象被創建和垃圾收集。
- 節點選擇了
(error,result)
整個回調。我建議遵循他們的論證順序來保持一致。 (而不是說(result1, result2, result3, error)
)
優點的承諾:
- 提供一個流暢的界面,有時可以幫助減輕嵌套回調地獄,如shown here。代碼似乎通過鏈接
.then(foo).then(bar)
調用線性流動。 - 一個好的承諾庫可以讓你在並行上運行很多異步操作,並且只有在它們全部完成後才能繼續。 Deferred庫通過
map
無縫地完成此操作,Q具有allResolved
,ES6承諾報價Promise.all()
。 (這也可以使用回調,例如使用async.parallel()
,但不是內置。) - 一個好的承諾庫將讓你指定一個錯誤處理函數,如果任何排隊的函數失敗將被調用。要使用回調來做到這一點,需要在每個回調開始時使用一點樣板:
if (err) return callback(err);
。
這將是有意義的使用回調附近底部堆,爲此,將每秒多次運行代碼。更高的堆棧,承諾可能會更好,因爲它們更易於閱讀和理解,並且可以更加優雅地處理錯誤。
值得注意的是,承諾可以在運行時從回調構建。因此,您可以用最低限度的回調形式實現您的核心代碼,並且如果您願意,仍然可以公開庫的承諾版本。 (如在Q.nfbind()
。)
我很想聽聽其他優點/缺點。
獎勵建議:總是處理錯誤!使用這兩種方法,如果您不處理錯誤,那麼它將簡單地消失,讓您在黑暗中爲什麼代碼無法按預期工作。
回調應始終處理
if (err) ...
和承諾應始終有.catch()
如果他們不返回。即使你期望的錯誤有時,並不需要處理那些不處理意外的錯誤意味着你不會聽到來自開發商的錯誤錯誤,如拼寫錯誤,如果代碼在未來發生變化。
Promises的替代
.catch()
的是聽取unhandled rejections。我個人使用這個來發出警告,.catch()
失蹤!
我一直在嘗試與此庫聲明的方式:http://chainsjs.org仍然更多的工作做就可以了,但它給你定義一個「執行地圖」在這裏你幾乎可以完全控制流量的能力從簡單的映射執行。
那個網站已經關閉,但今天我在檔案中找到[副本](http://web.archive.org/web/20141217011058/http://chainsjs.org/)。有一個其他控制流庫的列表[這裏](https://github.com/joyent/node/wiki/modules#user-content-wiki-async-flow)。 – joeytwiddle 2015-07-02 09:39:23
@joeytwiddle - 感謝您的提示,當github頁面更改IP時,我從未切換過IP。我剛剛更新了DNS,它應該很快就會備份。 – 2015-07-10 20:17:40
- 1. 回調還是承諾?
- 2. Node.js - 承諾和回調VS同步
- 3. Node.js承諾請求返回
- 4. 節點承諾控制流程
- 5. 解決承諾在服務中沒有控制器回調
- 6. 回覆承諾的承諾
- 7. 承諾是單播還是廣播?
- 8. Node.js Wit.ai承諾返回函數
- 9. node.js解析承諾並返回值
- 10. AngularJS承諾沒有回調?
- 11. 藍鳥承諾和回調
- 12. ES6承諾結算回調?
- 13. NodeJS:承諾內的回調
- 14. 從承諾中回報價值:回調或承諾?
- 15. 承諾鏈接+返回變量與流星迴調
- 16. Node.js控制流程
- 17. 我如何將這個承諾交還給控制器?
- 18. 控制回調流程
- 19. 然後()回調發射之前承諾解決在node.js
- 20. 通過node.js + Q進行同步回調延遲/承諾模塊
- 21. Node.js&co - 避免混合承諾和事件回調
- 22. 快速Node.JS - 接收Redis回調,執行承諾
- 23. 使用Bluebird在承諾中包裝Node.js回調
- 24. Javascript承諾:catch流
- 25. 流星與承諾?
- 26. 如何退還承諾
- 27. 等待承諾退還
- 28. 如何退還承諾?
- 29. 藍鳥承諾作爲承諾回調不知道api
- 30. 解析承諾數組node.js
關於perfs的更多信息:http://thanpol.as/javascript/promises-a-performance-hits-you-should-be-aware-of/ – Offirmo 2013-09-17 12:59:54
鏈接不再工作 – Shide 2017-01-25 09:13:06
這是[archived copy of Offirmo的PERF鏈接](http://web.archive.org/web/20160522044854/http://thanpol.as/javascript/promises-a-performance-hits-you-should-be-aware-of)。 – joeytwiddle 2017-01-25 10:35:56