欧美bbbwbbbw肥妇,免费乱码人妻系列日韩,一级黄片

從零學(xué)習node.js之詳解異步控制工具async(八)

 更新時間:2017年02月27日 11:23:55   作者:Wenzi  
sync是一個流程控制工具包,提供了直接而強大的異步功能。基于JavaScript為Node.js設(shè)計,同時也可以直接在瀏覽器中使用。下面這篇文章主要介紹了node.js之異步控制工具async的相關(guān)資料,需要的朋友可以參考下。

前言

大家在編寫異步程序時,最頭痛的就是不知道結(jié)果什么時候返回給我們,然后執(zhí)行后面的操作,很多時候只能把后面的操作放到返回成功的函數(shù)里,或者使用計數(shù)器等方法。

比較典型的兩個就是:后面的操作需要依賴上一個異步操作的結(jié)果;多個異步操作并行執(zhí)行,都執(zhí)行完成后再執(zhí)行接下來的操作。

這兩個操作中,第一個異步的程序我們可能會寫成這樣:

db.select(SQL1, function(res1){
 db.delete(SQL2, function(res2){
 db.insert(SQL3, function(res3){
 // ...
 })
 })
});

將后面的操作寫到執(zhí)行成功后的回調(diào)函數(shù)里。第2個并行的異步操作,可以使用計數(shù)器的方法,每個異步調(diào)用成功時,計數(shù)器加1,當所有的異步都調(diào)用成功后,再接著執(zhí)行:

var count = 0;
var success = function(){
 count++;
 if(count>=3){ 
  console.log('執(zhí)行完畢...');
 }
}

var select = function(){
 db.select(sql, function(res){
  success();
 })
}
var select2 = function(){
 db.select(sql, function(res){
  success();
 })
}
var select3 = function(){
 db.select(sql, function(res){
  success();
 })
}
select();
select2();
select3();

這些編寫方式非常麻煩,而且代碼邏輯比較混亂,調(diào)試起來也很不方便。那么就要用到異步控制的利器async了。

介紹

async的作用是進行流程的控制,而且提供了非常多的方法可供調(diào)用。

這些方法可以分為三大類:

  • 集合類(Collections)
  • 流程控制類(Control Flow)
  • 工具類(Utils)

下面我們從這三個分類里分別挑出幾個方法進行講解。

二、函數(shù)介紹

async中提供了非常多的方法可供使用,我們僅僅是講解其中幾個比較有代表性的,其他的可以訪問官方文檔:http://caolan.github.io/async/docs.html。

2.1 集合類

集合類中的方法主要有some, ‘map', ‘each', ‘every'等,這些方法是對數(shù)組或組合進行某個相同的操作后,統(tǒng)一執(zhí)行回調(diào)函數(shù)。

我們以map為例,map對集合中的每一個元素,執(zhí)行某個相同的異步操作,得到結(jié)果。所有的結(jié)果將匯總到最終的callback里。
使用方法,map接收三個參數(shù),分別是:

參數(shù)名稱 類型 說明
coll iteratee callback
Array | Iterable | Object function function
需要處理數(shù)組,集合或其他可迭代的類型 迭代方法,用來對集合中的每一項進行處理。該方法接收兩個參數(shù)(item, callback);item為集合中的每一項, callback為回調(diào)函數(shù)。callback需要帶有err(有時可能為null)和處理后的數(shù)據(jù),callback(err, data) 最終回調(diào)函數(shù),當集合處理完畢后調(diào)用此函數(shù),傳遞兩個參數(shù)err和result,result為之前處理后的所有的結(jié)果的集合

注意:中間處理函數(shù)iteratee對coll中的每一項都是并發(fā)處理的,因此并不能保證iteratee按照順序完成。不過,如果coll是個數(shù)組,最后的結(jié)果集results會按照coll中的順序排列;如果coll是個集合(Object)類型,results會是數(shù)組類型,結(jié)果將大致按照coll的鍵的順序排列(但是不同在不同的JavaScript引擎中會有可能發(fā)生變化)。

我們來舉個例子,使用map獲取幾個文件中的內(nèi)容:

var files = ['./file/cnode_1.txt', './file/cnode_2.txt', './file/cnode_3.txt'];

// 讀取文件內(nèi)容
// 第1個參數(shù) 文件名稱列表的數(shù)組
// 第2個參數(shù) 傳入數(shù)組中的每一項和回調(diào)函數(shù)
// 第3個參數(shù) results為所有結(jié)果的集合
async.map(files, function(file, cb){
 fs.readFile(file, 'utf-8', function(err, data){
  cb(err, data);
 })
}, function(err, results){
 console.log( results );
})

而且,如果中間的處理函數(shù)比較大,不想寫在map中,也可以單獨寫成一個函數(shù),然后傳遞進去,不過參數(shù)傳遞還是要符合規(guī)則的:

var files = ['./file/cnode_1.txt', './file/cnode_2.txt', './file/cnode_3.txt'];

var read = function(file, cb){
 fs.readFile(file, 'utf-8', function(err, data){
  cb(err, data);
 })
}
async.map(files, read, function(err, result){
 console.log( result );
})

這里還有一個mapLimit,可以傳遞一個參數(shù)limit,用來限制并發(fā)的數(shù)量:mapLimit(coll, limit, iteratee, callbackopt)

// 并發(fā)數(shù)量為2
async.mapLimit(files, 2, read, function(err, result){
 console.log( result );
})

同時,集合類中還有其他的方法,我們也稍微了解下:

  1. each : 與map類似,但是最后的回調(diào)函數(shù)里沒有results,each只循環(huán)不負責處理結(jié)果
  2. every : 中間處理函數(shù)iteratee的參數(shù)(err, boolean)需要傳遞一個boolean值,若所有選項的結(jié)果都為true,則results為true
  3. some : 與every類似,只是只要其中一個選項的結(jié)果為true,則results為true
  4. filter : 對coll進行篩選,篩選出結(jié)果為true的結(jié)果
  5. reject : 與filter正好相反,篩選出結(jié)果為false的結(jié)果
  6. concat : 將每個異步操作的結(jié)果合并為一個數(shù)組

2.2 流程控制類

上面的集合類是對一個集合進行相同的處理,集合中的每一項都處理完后,再對結(jié)果進行回調(diào)處理。而多個回調(diào)方法執(zhí)行時,則需要對這幾個回調(diào)方法進行控制了。

多個回調(diào)方法執(zhí)行時,通常有這么幾個流程:

  1. 串行且無關(guān)聯(lián),即執(zhí)行完一個后再依次執(zhí)行下一個,且相互之間無數(shù)據(jù)交互,都執(zhí)行完后,再執(zhí)行最后的回調(diào)函數(shù)??梢允褂?code>async.series
  2. 串行且有關(guān)聯(lián),即執(zhí)行完一個后再依次執(zhí)行下一個,且上一個回調(diào)函數(shù)的結(jié)果會作為下一個回調(diào)函數(shù)的參數(shù)??梢允褂胊sync.waterfall
  3. 并行,這幾個回調(diào)函數(shù)同時并發(fā)執(zhí)行,都執(zhí)行完成后,再執(zhí)行最后的回調(diào)函數(shù)。可以使用async.parallel

當然還有其他更復(fù)雜的流程,這里也只聊上面的三種情況。

async.series,async.waterfall和async.parallel的語法都是一樣的:
async.Method(coll, function(err, results){

})

其中coll既可以是數(shù)組,也可以是json格式的,而且results的類型與coll對應(yīng)。

串行且無關(guān)聯(lián)async.series

// 串行且無關(guān)聯(lián),數(shù)組格式
async.series([
 function(cb){
  getAllList(function(result){
   cb(null, result);
  });
 },
 function(cb){
  getAllUser(function(result){
   cb(null, result);
  });
 }
], function(err, result){
 console.log(result);
})

同時串行的異步可以是json格式的:

// 串行且無關(guān)聯(lián),json個數(shù)
async.series({
 one: function(cb){
  getAllList(function(result){
   cb(null, result);
  });
 },
 two: function(cb){
  getAllUser(function(result){
   cb(null, result);
  });
 }
}, function(err, result){
 console.log(result);
})

串行且有關(guān)聯(lián)async.waterfall

// 串行且上一個結(jié)果作為下一個的參數(shù)
async.waterfall([
 function(cb){
  getListById(1, function(result){
   cb(null, result);
  });
 },
 function(params, cb){
  console.log(params);
  getAllUser(function(result){
   cb(null, result);
  });
 }
], function(err, result){
 console.log(result);
})

并行async.parallel

// 并行,getAllList與getAllUser同時執(zhí)行
async.parallel([
 function(cb){
  getAllList(function(result){
   cb(null, result);
  });
 },
 function(cb){
  getAllUser(function(result){
   cb(null, result);
  });
 }
], function(err, result){
 console.log(result);
})

關(guān)于并行的異步操作,這里還有一個async.parallelLimit,限制并發(fā)的數(shù)量:

// 并發(fā)數(shù)量為2
async.parallelLimit([
 iteratee1, iteratee2, iteratee3, ...
], 2, function(err, results){
 
})

2.3 工具類

async中也提供了不少的工具方法可供使用,比如async.log可以輸出回調(diào)方法中的值,第1個參數(shù)為函數(shù),后面的參數(shù)為傳遞給函數(shù)的參數(shù):

var hello = function(name, callback) {
 setTimeout(function() {
  callback(null, 'hello ' + name);
 }, 1000);
};

// 將'world'傳遞給hello方法
async.log(hello, 'world'); // 'hello world'

這里面還有apply, dir, timeout等方法。

總結(jié)

使用async控制異步流程非常的方便,而且也可以在前端使用,比如可以操作多個ajax請求等。好了,以上就是這篇文章的全部內(nèi)容了,希望本文的內(nèi)容對大家的學(xué)習或者工作能帶來一定的幫助,如果有疑問大家可以留言交流,謝謝大家對腳本之家的支持。

相關(guān)文章

  • Nodejs 微信小程序消息推送的實現(xiàn)

    Nodejs 微信小程序消息推送的實現(xiàn)

    這篇文章主要介紹了Nodejs 微信小程序消息推送的實現(xiàn),文中通過示例代碼介紹的非常詳細,對大家的學(xué)習或者工作具有一定的參考學(xué)習價值,需要的朋友們下面隨著小編來一起學(xué)習學(xué)習吧
    2021-01-01
  • node.js實現(xiàn)簡單爬蟲示例詳解

    node.js實現(xiàn)簡單爬蟲示例詳解

    這篇文章主要為大家介紹了node.js實現(xiàn)簡單爬蟲示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪
    2023-04-04
  • node使用Git Bash作為命令行終端示例

    node使用Git Bash作為命令行終端示例

    這篇文章主要為大家介紹了node使用Git Bash作為命令行終端示例詳解,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪
    2023-08-08
  • nodejs語言實現(xiàn)驗證碼生成功能的示例代碼

    nodejs語言實現(xiàn)驗證碼生成功能的示例代碼

    這篇文章主要介紹了nodejs語言實現(xiàn)驗證碼生成功能的示例代碼,文中通過示例代碼介紹的非常詳細,對大家的學(xué)習或者工作具有一定的參考學(xué)習價值,需要的朋友們下面隨著小編來一起學(xué)習學(xué)習吧
    2019-10-10
  • node省市區(qū)三級數(shù)據(jù)性能測評實例分析

    node省市區(qū)三級數(shù)據(jù)性能測評實例分析

    這篇文章主要介紹了node省市區(qū)三級數(shù)據(jù)性能,結(jié)合具體實例形式評測分析了node省市區(qū)三級數(shù)據(jù)的實現(xiàn)、改進方法與運行效率,需要的朋友可以參考下
    2019-11-11
  • nodejs如何獲取時間戳與時間差

    nodejs如何獲取時間戳與時間差

    本文詳細介紹了nodejs獲取時間戳與時間差的多種方法,對平時nodejs的使用很有幫助,下面一起來看看吧。
    2016-08-08
  • node?NPM庫glob通配符匹配文件名minimatch模式匹配字符串學(xué)習

    node?NPM庫glob通配符匹配文件名minimatch模式匹配字符串學(xué)習

    這篇文章主要為大家介紹了node?NPM庫glob通配符匹配文件名minimatch模式匹配字符串學(xué)習,有需要的朋友可以借鑒參考下,希望能夠有所幫助,祝大家多多進步,早日升職加薪
    2023-07-07
  • nodejs微信開發(fā)之授權(quán)登錄+獲取用戶信息

    nodejs微信開發(fā)之授權(quán)登錄+獲取用戶信息

    這篇文章主要介紹了nodejs微信開發(fā)之授權(quán)登錄+獲取用戶信息,小編覺得挺不錯的,現(xiàn)在分享給大家,也給大家做個參考。一起跟隨小編過來看看吧
    2019-03-03
  • 理解nodejs的stream和pipe機制的原理和實現(xiàn)

    理解nodejs的stream和pipe機制的原理和實現(xiàn)

    本篇文章主要介紹了理解nodejs的stream和pipe機制的原理和實現(xiàn),具有一定的參考價值,感興趣的小伙伴們可以參考一下
    2017-08-08
  • npm出現(xiàn)Cannot?find?module?'XXX\node_modules\npm\bin\npm-cli.js'錯誤的解決方法

    npm出現(xiàn)Cannot?find?module?'XXX\node_modules\npm\bin\np

    最近在啟動項目的時候會報這個錯就是npm丟失,所以下面這篇文章主要給大家介紹了關(guān)于npm出現(xiàn)Cannot?find?module?'XXX\node_modules\npm\bin\npm-cli.js'錯誤的解決方法,需要的朋友可以參考下
    2022-08-08

最新評論