javascript異步處理與Jquery deferred對象用法總結(jié)
本文實例講述了javascript異步處理與Jquery deferred對象用法。分享給大家供大家參考,具體如下:
這是項目組老大整理的一些關(guān)于jquery 異步處理請求,以及使用 jquery deferred 對象的一些常見方法。雖然是項目上總結(jié)出來的。但也比較通用,分享在這里。
- 所有的Ajax操作都采用異步處理。
- 采用Jquery的Deffered對象來處理異步調(diào)用。
- 因為是異步調(diào)用,所以
$.Ajax函數(shù)的返回值不代表返回的結(jié)果,只是一個Deffered對象。 - Ajax調(diào)用完成后執(zhí)行的邏輯可以寫成函數(shù)作為參數(shù)傳遞給Deffered對象的
done(),fail(),always()函數(shù)來執(zhí)行。 - 如果一個函數(shù)包含Ajax調(diào)用,那么這個函數(shù)必須將Ajax返回的異步對象作為自己的返回值,否則函數(shù)的調(diào)用者無法保證后續(xù)代碼的正常執(zhí)行順序。
例如:
function readData(){
$.ajax({ url:"test", dataType:"json" })
.done(function() {
//....
});
}
readData();
//...這里想添加一些后續(xù)處理,但程序?qū)⒃贏jax回調(diào)前執(zhí)行,所以無法達到預(yù)期目的
正確的代碼:
function readData(){
return $.ajax({ url:"test", dataType:"json" })
.done(function() {
//....
});
}
readData().done(function () {
//...想添加的后續(xù)處理可以加在這里處理
});
- 如果需要調(diào)用多個Ajax請求,請注意Ajax請求是否可以同時進行,如果可以應(yīng)該使用
when()函數(shù)來同時執(zhí)行,以提高程序的運行效率和可讀性。 - deferred對象有一個方法
promise(),可以阻止其他代碼修改deferred對象的狀態(tài),也就是其他代碼調(diào)用reslove()和reject()無效。
var dtd = $.Deferred(); // 新建一個Deferred對象
var wait = function(dtd){
var tasks = function(){
alert("執(zhí)行完畢!");
dtd.resolve(); // 改變Deferred對象的執(zhí)行狀態(tài)
};
setTimeout(tasks,5000);
return dtd;
};
wait(dtd)
.done(function(){ alert("成功了!"); })
.fail(function(){ alert("出錯啦!"); });
dtd.resolve(); //這里修改了dtd對象的狀態(tài),導(dǎo)致立刻出現(xiàn)“成功了!”的提示
正確的例子:
var dtd = $.Deferred(); // 新建一個Deferred對象
var wait = function(dtd){
var tasks = function(){
alert("執(zhí)行完畢!");
dtd.resolve(); // 改變Deferred對象的執(zhí)行狀態(tài)
};
setTimeout(tasks,5000);
return dtd.promise(); // 返回promise對象
};
wait(dtd)
.done(function(){ alert("成功了!"); })
.fail(function(){ alert("出錯啦!"); });
dtd.resolve(); //這里修改dtd對象的狀態(tài)無效
- 一些情況的處理:
1.嵌套異步操作的處理。
如果一個函數(shù)內(nèi)部執(zhí)行異步任務(wù),并且在異步任務(wù)的done回調(diào)內(nèi)會嵌套另一個異步任務(wù),那么簡單返回第一個異步任務(wù)的返回值是不行的,需要另外自行定義一個Deferred對象作為返回值。
function loadComponent(id){
var dtd = $.Deferred();
//loadScript將異步加載一個js文件,所以返回值是一個Deffered對象
return loadScript(id)
.done(function() {
//js加載后,觸發(fā)component的load事件,此事件內(nèi)將使用Ajax獲取頁面模板和數(shù)據(jù),生成最終的html
app.getComponent(id).trigger("load")
.done( function(){
dtd.reslove(agruments);
}).fail( function(){
dtd.reject(agruments);
});
});
//返回自定義的dtd對象,才能保證返回值的done回調(diào)在load事件完成后執(zhí)行
return dtd;
}
2.一個函數(shù)內(nèi)同時包含同步和異步case的處理。
/* 這個函數(shù)返回一個異步對象,當(dāng)異步對象執(zhí)行done時,表示component被加載完成 */
function requireComponent(id){
if (this.components[id]){
//如果component已經(jīng)被加載,直接返回一個reslove的異步對象,否則返回值內(nèi)容與else分支不同,后續(xù)代碼難以處理
var dtd = $.Deferred();
dtd.reslove(this.getComponent(id));
return dtd;
}
else{
//如果component未被加載,loadScript將異步加載JavaScript并執(zhí)行,然后將被加載的component放入this.components
return loadScript(id);
}
}
- Jquery異步模型有一個缺點,就是缺乏類似
wait操作的處理能力,如果多個異步調(diào)用要順序發(fā)生時,就要在done里面嵌套處理,影響代碼可讀性.
aSyncTask1.done( function () {
//...第一個操作完成后的處理
asyncTask2.done( function () {
//...第二個操作完成后的處理
asyncTask3.done( function () {
//...第三個操作完成后的處理
});
})
})
更多關(guān)于jQuery相關(guān)內(nèi)容感興趣的讀者可查看本站專題:《jQuery form操作技巧匯總》、《jQuery文件與目錄操作技巧匯總》、《jquery中Ajax用法總結(jié)》、《jQuery擴展技巧總結(jié)》、《jquery選擇器用法總結(jié)》及《jQuery常用插件及用法總結(jié)》
希望本文所述對大家jQuery程序設(shè)計有所幫助。
相關(guān)文章
DOM事件階段以及事件捕獲與事件冒泡先后執(zhí)行順序(圖文詳解)
DOM事件標準定義了兩種事件流,這兩種事件流有著顯著的不同并且可能對你的應(yīng)用有著相當(dāng)大的影響。這兩種事件流分別是捕獲和冒泡。和許多Web技術(shù)一樣,在它們成為標準之前,Netscape和微軟各自不同地實現(xiàn)了它們,下面介紹DOM事件階段以及事件捕獲與事件冒泡先后執(zhí)行順序2015-08-08
jQuery中的for循環(huán)var與let的區(qū)別
這篇文章主要介紹了jQuery中的for循環(huán)var與let的區(qū)別 ,非常不錯,具有參考借鑒價值,需要的朋友可以參考下2018-04-04
jQuery Mobile操作HTML5的常用函數(shù)總結(jié)
jQuery Mobile是針對移動端開發(fā)的JavaScript框架,正如其名基于jQuery庫,jQuery Mobile主要被用來操作HTML5設(shè)計頁面UI,下面就來看一下jQuery Mobile操作HTML5的常用函數(shù)總結(jié):2016-05-05
jquery ui bootstrap 實現(xiàn)自定義風(fēng)格
本文主要是給大家分享了jQuery UI bootstrap的自定義風(fēng)格,以及自定義的方法,非常的實用,有需要的小伙伴千萬不要錯過2014-11-11

