亚洲在线久爱草,狠狠天天香蕉网,天天搞日日干久草,伊人亚洲日本欧美

章節
問答
課簽
筆記
評論
占位
占位

Deferred的執行流程

用下面的例子分析(見右側代碼編輯器):

var defer = $.Deferred();
defer.resolve(5);
defer.done(function(value) {})
var filtered = defer.then(function(value) {
  return value * 2;
});
filtered.done(function(value) {});

這里有幾個關鍵的問題:

1、defer延時對象通過resolved觸發done成功回調,調用在添加done之前,那么靠什么延時處理?

2、為什么defer.then對象返回的給filtered.done的數據可以類似管道風格的順序疊加給后面的done處理?

一般來說,javascript要實現異步的收集,就需要“等待”,比如defer.resolve(5)雖然觸發了,但是done的處理還沒添加,我們必須要等待done、then等方法先添加了后才能執行了resolve,那么常規的的用法就是在resolve內部用setTimeout 0,image.onerror行成一個異步的等待操作處理。

但是jQuery很巧妙的繞過了這個收集方式,

defer.resolve(5)方法實際就是觸發了callback回到函數的fireWith方法,這樣可以接受一個上下文deferred與參數5

deferred[tuple[0] + "With"](this === deferred ? promise : this, arguments);

之前 done | fail | progress方法都是通過jQuery.Callbacks("once memory") 或 jQuery.Callbacks("memory")生成的。

實際上在Callback源碼fire方法有一句 memory = options.memory && data;這樣就很巧妙的緩存當前參數5的值,提供給下一個使用,這個就是then,pipe鏈式數據的一個基礎了,此刻的操作,我們把memory保存了這個數據的值。

重點來了,下一個defer.done的操作也是走的add的處理,把done的回調函數加入到list隊列中的之后,接著就會觸發。

 // With memory, if we're not firing then
 // we should call right away
} else if (memory) {
  firingStart = start;
  fire(memory);
}

因為memory在上一個resolve操作的時候,緩存了5了,所以memory的判斷顯示是為真的,所以立刻就觸發了fire(memory)的代碼了,所以就算觸發的循序與添加的循序不一致,也不會導致錯誤。 而且jquery很巧妙的避免了異步收集的問題,這樣處理更可靠了。可見回調函數模塊就是為Deferred模塊量身定做的了。

第二個問題,是關于then,pipe管道風格的處理,這樣也是一個很復雜的設計,在后面一章就提到了。

任務

?不會了怎么辦
||

提問題

寫筆記

公開筆記
提交
||

請驗證,完成請求

由于請求次數過多,請先驗證,完成再次請求

加群二維碼

打開微信掃碼自動綁定

您還未綁定服務號

綁定后可得到

  • · 粉絲專屬優惠福利
  • · 大咖直播交流干貨
  • · 課程更新,問題答復提醒
  • · 賬號支付安全提醒

收藏課程后,能更快找到我哦~

使用 Ctrl+D 可將課程添加到書簽

邀請您關注公眾號
關注后,及時獲悉本課程動態

舉報

0/150
提交
取消
全部 精華 我要發布
全部 我要發布
最熱 最新
只看我的

手記推薦

更多

本次提問將花費2個積分

你的積分不足,無法發表

為什么扣積分?

本次提問將花費2個積分

繼續發表請點擊 "確定"

為什么扣積分?