macro-task和micro-task 简介

先看下面的代码


上面的执行结果是1,3,2
原因:上面的setTimeout可以理解为异步函数调用,因为javascript是单线程的,主线程拥有一个执行栈和一个事件循环
当代码开始执行的时候,主线程会依次执行代码(就是script里面的代码),当遇到异步函数的时候(setTimeout),会将该函数加入到任务队列里面,然后继续执行,当主线程空闲后,然后把异步函数出栈,直到所有的异步函数执行完毕即可。

在一个浏览器环境中,只能有一个事件循环,但是可以有多个任务队列,而每个任务都有一个任务源,相同任务源的任务,只能放到一个任务队列中

上面的micro-task和macro-task就是两种不同的任务队列
macro-task:script(script标签里面的整体代码) setTimeout,setInterval,setImmediate,I/O,UI rendering
micro-task:process.nextTick,Promise,MutationObserver

具体流程

首先:全部代码(script)算一个macrotask.。
第一步:浏览器先执行一个macrotask;执行的过程中,创造了新的macrotask(setTimeout之类的),然后接着执行,把promise加入到micro-task队列里面
第二步:浏览器执行microtask(例如promise),这里会将microtask里面所有任务都取出
第三步:重复,浏览器会再执行一个macrotask
总的来说:macrotask每次只取一个,而microtask会一次取完

下面再来另外一个例子:


上面的输出结果是 1,5,3,4,2

具体流程大概是下面这样:

当代码开始执行的时候,会先输出1,然后把setTimeout加入到一个macrotask 队列里面,接着把promise加入到microtask 队列里面,然后输出5
到这里我们代码执行完了一个macrotask(script里面的代码算第一个macrotask),接着要开始执行microtask,这次会把microtask里面所有的任务都执行完,这里就输出3和4,
当microtask执行完后,又会接着开始执行macrotask,就是setTimeout,到这里输出完2后,所有代码就都执行完毕

你可能感兴趣的:(macro-task和micro-task 简介)