在看js事件循环机制的解释时,经常看到如下说明:
任务队列分为
macro-task
(宏任务)与micro-task
(微任务),在最新标准中,它们被分别称为task
与jobs
。
macro-task
大概包括:script(整体代码)
,setTimeout
,setInterval
,setImmediate
,I/O
,UI rendering
。
micro-task
大概包括:process.nextTick
,Promise
,Object.observe
(已废弃),MutationObserver
(html5新特性)
而后开始解释事件循环的流程,当执行栈为空时,事件循环先从一个macro-task
开始,然后执行所有的micro-task
,再执行一个macro-task
,balabala...
那么问题来了,在第一次执行事件循环的时候,通常都会这样说
事件循环从宏任务队列开始,这个时候,宏任务队列中,只有一个
script(整体代码)
任务。
想知道script(整体代码)
是怎么作为macro-task
入栈的?
比如说,setTimeout
和ajax
在浏览器中都有对应的webApi模块去处理,script(整体代码)
应该是先编译成指令存在指令区,然后开始执行的吧。这个过程是怎么变成task任务,进而添加到队列里的,为啥不是直接入栈呢?
求各位大神解答!
那这道题目举例吧。
为什么输出结果是1,2,3,5,4而非1,2,3,4,5?
既然你已经知道怎么分类了,不就不赘述了。直接说说macrotasks和microtasks的执行顺序吧:
可以认为macro是主人,micro是奴隶,哪个macro创建了micro,micro就管它叫主人。
ma1快死之前,对奴隶mi1说,我要挂了,你一起陪葬吧,mi1说好的便上吊了,ma1看mi1死后,也就安心的去了。
然后ma2也准备要死了,,,
总的来说就是,macro作为主导,它有支配micro的能力,在一个macro任务消灭之前,它会让它创建的micro任务都执行完,然后才进入下一个macro任务。
然后,入栈出栈,这个另一个概念,是每个task执行它的代码的时候发生的,比如变量定义,函数调用,通过栈的入出,计算出结果。