新手如何快速理解js异步编程

  

  

异步编程从早期的回调,事件发布\订阅模式到ES6的承诺,发电机在到ES2017中异步,看似风格迥异,但是还是有一条暗线将它们串联在一起的,就是希望将异步编程的代码表达尽量地贴合自然语言的线性思维。
  

  

以这条暗线将上述几种解决方案连在一起,就可以更好地理解异步编程的原理,魅力。
  ├──事件发布\订阅模式& lt;=回调
  ├──承诺& lt;=事件发布\订阅模式
  ├──异步等待& lt;=承诺,发电机

  

  

这个模式本质上就是回调函数的事件化。它本身并无同步,异步调用的问题,我们只是使用它来实现事件与回调函数之间的关联。比较典型的有NodeJS的事件模块
  

        const {EventEmitter}=要求(“事件”)   const eventEmitter=new eventEmitter ()//订阅   eventEmitter。(“事件”,函数(味精){   控制台。日志(“事件”,味精)   })//发布   eventEmitter。发出(“事件”,“Hello world”)      

那么这种模式是如何与回调关联的呢?我们可以利用Javascript简单实现EventEmitter,答案就显而易见了。
  

        类usrEventEmitter {   构造函数(){   这一点。听众={}   }//订阅,回调为每个事件的侦听器   (eventName,回调){   如果(! this.listeners [eventName])。听众[eventName]=[]   this.listeners [eventName] .push(回调)   }//发布   发出(eventName params) {   this.listeners [eventName]。forEach(回调=比;{   回调(params)   })   }//注销   (eventName,回调){   const休息=this.listeners [eventName]。fitler (elem=比;elem !==回调)   这一点。听众[eventName]=休息   }//订阅一次   一次(eventName,回调){   常量处理程序=function () {   回调()   这一点。(eventName处理程序)   }   这一点。(eventName处理程序)   }   }      

上述实现忽略了很多细节,例如异常处理,多参数传递等。只是为了展示事件订阅\发布模式。

  

很明显的看的出,我们使用这种设计模式对异步编程做了逻辑上的分离,将其语义化为
  

     //一些事件可能会被触发   eventEmitter.on//当它发生的时候,要这样处理   eventEmitter.emit      

也就是说,我们将最初的调变成了事件监听器,从而优雅地解决异步编程。

  


  

  

使用事件发布\订阅模式时,需要我们事先严谨地设置目标,也就是上面所说的,必须要缜密地设定好有哪些事件会发生。这与我们语言的线性思维很违和。那么有没有一种方式可以解决这个问题,社区产出了承诺。
  

        const承诺=新的承诺(函数(解决,拒绝){
尝试{
setTimeout(()=比;{
解决(“hello world”)
}, 500)
}捕捉(错误){
拒绝(错误)
}
})
//语义就变为先发生一些异步行为,然后我们应该这么处理   的承诺。然后(味精=比;console.log(味精))。抓住(错误=比;控制台。日志(“犯错”,错误))      

那么这种承诺与事件发布\订阅模式有什么联系呢?我们可以利用EventEmitter来实现承诺,这样可能会对你有所启发。
  

  

我们可以将视承诺为一个EventEmitter,它包含了{状态:“等待”}来描述当前的状态,同时侦听它的变化

  
      <李>当成功时{状态:“满足”},要做些什么>   const {EventEmitter}=要求(“事件”)   类usrPromise延伸EventEmitter {//构造时候执行   构造函数(执行者){   super ()//发布   const解决=(值)=比;这一点。发出(“解决”,值)   const拒绝=(原因)=比;这一点。发出(“拒绝”,原因)   如果(执行者){//模拟事件循环,注此处利用Macrotask来模拟Microtask   setTimeout(()=比;遗嘱执行人(解决,拒绝))   }   }   然后(resolveHandler rejectHandler) {   const nextPromise=new usrPromise ()//订阅解决事件   如果(resolveHandler) {   const解决=(数据)=比;{   const结果=resolveHandler(数据)   nextPromise。发出(‘解决’,结果)   }   这一点。(“解决”,解决)   }//订阅拒绝事件   如果(rejectHandler) {   const拒绝=(数据)=比;{   const结果=rejectHandler(数据)   nextPromise。发出(“拒绝”,结果)   }   这一点。(“拒绝”,拒绝)   其他}{   这一点。(“拒绝”,(数据)=比;{   的承诺。发出(“拒绝”,数据)   })   }   返回nextPromise   }   抓住(处理器){   这一点。(“拒绝”,处理程序)   }   }

    新手如何快速理解js异步编程