前端異步流程工具

前端異步流程工具

傳統:

回調函數

流行:

  1. Promise *最流行
const p1 = new Promise ( function ( resolve, reject ) { resolve( '任務一' ) }) .then ( function ( data ) { console.log( data ) }) const p2 = new Promise ( function ( resolve, reject ) { setTimeout( function () { resolve( '任務二' ) },1000) }) .then ( function ( data ) { console.log( data ) }) console.log( '主線程任務 ') // Promise // .all([p1,p2]) // 先執行all中全部任務, 執行完成以後再去執行後面的任務 // .then( data => { // console.log( '任務3' ) // }) Promise .race([p1,p2]) // race 誰快輸出誰 .then( data => { console.log( '任務3' ) }) 
  1. Generator函數
    1. 概念,在function 關鍵字後面寫一個* ,表示一個generator函數,generator經過 yield 關鍵字來定義任務
    2. 使用
function* p1 () { yield '任務1'; yield '任務2'; yield '任務3'; yield '任務4'; yield '任務5'; yield function* p2() { yield '任務7' } return '任務6' } var p = p1() console.log(p.next()) console.log(p.next()) console.log(p.next()) console.log(p.next()) console.log(p.next()) console.log(p.next()) console.log(p.next()) 
  1. Async函數 *最流行
    1. es6提供的async函數,async函數的底層其實就是generator函數
    2. async函數須要和關鍵字 await 搭配使用
    3. async也是promise,也能夠調用.then()
    4. 注意:只有await後面的任務順利執行完成,那麼下面的任務纔會去執行,若是awiat後面的任務執行不順利,那麼後面的任務會出問題
    5. 使用場景:先進行數據請求,獲得數據以後,再去操做這個數據,這個時候,咱們的async函數就是首選
    6. 如下是使用格式
    //格式1,將async放在箭頭函數參數的前面 var asyncFn=async ()=>{ var req=await '任務1' console.log(req) console.log('任務3') } asyncFn() console.log('任務2') //輸出任務2--任務1--任務3 任務2在主線程上,最早運行,其餘的在任務隊列中,哪一個在前那個先輸出 var asyncFn=async ()=>{ var req=await '任務1' console.log('任務3') console.log(req) } asyncFn() console.log('任務2') //輸出任務2--任務3--任務1 
    //格式2 對象 async放在函數名前面 var obj={ async aa(){ var data=await '任務1' var res=data console.log(res) } } obj.aa() 
  2. Node.js node.js提供的兩個方法
    1. process.nextTick(),在事件輪詢以前執行,防止I/O飢餓
    2. setImmediate(),在事件輪詢以後執行,防止輪詢阻塞
    3. 總結:
      • nextTick()的回調函數執行的優先級要高於setImmediate();
      • process.nextTick()屬於idle觀察者,setImmediate()屬於check觀察者.在每一輪循環檢查中,idle觀察者先於I/O觀察者,I/O觀察者先於check觀察者
      • idle觀察者,也就是事件輪詢最早進行的任務
      • I/O觀察者, 也就是事件輪詢中的任務(任務中的回調函數)
      • check觀察者 事件輪詢中的任務的結束
      • 在具體實現上,process.nextTick()的回調函數保存在一個數組中,setImmediate()的結果則是保存在鏈表中.
      • 在行爲上,process.nextTick()在每輪循環中會將數組中的回調函數所有執行完,而setImmediate()在每輪循環中執行鏈表中的一個回調函數.
    4. 使用格式:
      • process.nextTick( callback )
      • setImmediate( callback )
    5. 執行順序:
      • nextTick> setImmediate
      • nextTick 中 的nextTick > 外層的setImmediate
      • 外層setImmediate > 內層的setImmediate
    process.nextTick(function(){ console.log('1') process.nextTick(()=>{ console.log('3') }) }) setImmediate(function(){ console.log('b') }) process.nextTick(function(){ console.log('2') }) console.log('主線程') 
  3. 第三方 async.js 庫 串行series 並行parallel
    1. js文件引入另外一個js文件,須要使用模塊化引入,首先建立package.json文件,再下載async包
    2. 格式
      • series格式:async.series({},(err,data)=>{})
      • parallel格式:async.series({},(err,data)=>{})
//引入async模塊 var async=require('async') //串行 async.series({//以耗時最多的任務爲主,結束才能走過去 one:function(callback){ callback(null,'任務1') }, two:function(callback){ setTimeout(()=>{ callback(null,'任務2') },1000) } },(err,data)=>{ console.log(data) }) 
//引入async模塊 var async=require('async') // async.parallel({//等待最長的耗時結束,先輸出耗時短的,在輸出耗時長的 one:(callback)=>{ setTimeout(()=>{ callback(null,'任務1') },2000) }, two:(callback)=>{ setTimeout(()=>{ callback(null,'任務2') },1000) } },(error,data)=>{ console.log(data) })
相關文章
相關標籤/搜索