一、事件循环是什么?
首先,JS是单线程的,意味着同一时间内只能做一件事,但是这并不意味着单线程就是阻塞,而实现单线程非阻塞的方法就是事件循环机制。在JS中把任务分为同步和异步,同步任务和异步任务的执行环境不同,同步任务会进入主线程,异步任务会进入EventQueue(事件队列),主线程中的任务执行完毕后,回去EventQueue中读取对应的任务,并推到主线程中执行,不断重复过程,称为EventLoop(事件循环机制) 理解这里很重要!
二、同步任务、异步任务(宏、微)执行流程
任务又分为同步任务和异步任务,异步任务又分为(宏任务和微任务)
同步任务:立即执行的任务,同步任务一般会直接进入到主线程中执行
异步任务:异步执行的任务,比如promise、setTimeout定时函数等
我们可以这样理解同步任务和异步任务:
第一步:执行Script代码块,任务进入执行栈中
第二步:判断该任务是同步任务还是异步任务
第三步:如果是同步任务,则同步任务进入主线程;如果是异步任务,异步任务进入Event Table(事件表)注册回调函数,然后进入Event Queue(事件队列)准备执行(此时还未执行);
第四步:执行主线程中的同步任务,当同步任务执行完毕后,有,执行栈执行事件队列中的异步任务
第五步:执行异步任务的时候,先执行微任务,再执行一个宏任务,当这个宏任务执行完毕后再检查事件队列中是否还有微任务,如果还有就执行微任务,再执行一个宏任务,重复上述操作,知道所有异步任务执行完毕。
整个流程就是我们说的事件循环机制(Event Loop)
三、常见的微任务有:
- Promise.then
- Proxy对象替代
- process.nextTick
- MutaionObserver
四、常见的宏任务有:
- 整个script
- setTimeout/setInterval
- UI rendering/UI事件
- setImmediate、I/O
事件循环、宏任务、微任务关系:执行一个宏任务,如果遇到微任务就将它放到微任务的事件队列中,当前宏任务执行完成后,会查看微任务的事件队列,然后将里面的所有微任务依次执行完