该位与macrotask
和microtask
队列的描述混淆了。
对于“事件循环”的每个循环,一个宏任务都在其中完成 宏任务队列。该宏任务完成后,事件循环 访问微任务队列。整个微任务队列已完成 在继续之前。
setTimeout(function() {
console.log('macrotask');
}, 0);
Promise.resolve().then(function() {
console.log('microtask 1');
}).then(function() {
console.log('microtask 2');
});
该代码不是应该首先输出“ macrotask”吗? setTimeout是宏任务队列的一部分,该宏任务队列是在循环转到微任务队列之前完成的?
答案 0 :(得分:0)
您的代码正在运行的任务实际上是macrotask
。
完成后(这意味着评估和运行代码),事件循环将执行队列中的微任务。那是第一个承诺,但是那个承诺给微任务q添加了另一个承诺,第二个承诺被执行。
清除微任务q后,将选择另一个宏任务,并最终执行timeout
。
答案 1 :(得分:0)
在执行任何JS文件时,JS引擎会将内容包装在函数中,并将该函数与启动或启动事件关联。 JS引擎发出开始事件,事件被添加到任务队列中(作为宏任务)。
在初始化时,JS引擎首先提取宏任务队列中的第一个任务并执行回调处理程序。这样,我们的代码就运行了。
因此,我们看到正在运行的脚本是排队的第一个macrotask
。因此,首先JSEngine将脚本中的所有同步代码添加为事件循环队列中的macrotask
。然后,它看到setTimeout
是另一个macrotask
,因此它被记录在事件循环队列中的单独任务中。然后,它看到Promise是microtask
,并将其添加到 microtask 队列中。
只要没有其他回调,微任务队列就会在回调之后进行处理 JavaScript是中间执行的,并且在每个任务结束时。
因此,在这种情况下,任务队列的顺序为 Script => Promise1 => Promise2 => setTimeout
由于脚本中没有同步代码,因此脚本的执行不打印任何内容。然后Engine执行 microtask 队列(promise-1,promise-2),最后执行setTimeout
宏任务。
注意:-这是默认行为,在不同的浏览器中可能会有所不同。