鍍金池/ 問答/HTML/ 如何理解process.nextTick(fn) 早于 setTimeout(f

如何理解process.nextTick(fn) 早于 setTimeout(fn,0) 執(zhí)行

function compareFunc () {
  console.log(1);
  setTimeout(function () {
    console.log(2);
  }, 1);
  process.nextTick(function () {
    console.log(3);
  });
  setTimeout(function () {
    console.log(4);
  }, 0);
}
compareFunc();
// 執(zhí)行結(jié)果:
//1
//3
//2
//4

Fppv-U2FJpIUbOcXMYMWyy6-Aj5k

這個(gè)圖該怎么理解。根據(jù)這個(gè)圖,timers 不是在dile觀察者前面嗎?

回答
編輯回答
久不遇

nextTick屬于microTask, 而setTimeout屬于macroTask. 一個(gè)macroTask執(zhí)行完后會(huì)插入多個(gè)microTask.

這里的macroTask不只是setTimeout, 還有主線程的運(yùn)行腳本. 比如你的compareFunc函數(shù), 運(yùn)行的時(shí)候聲明兩個(gè)異步任務(wù).

此時(shí)nextTick被插入主線程腳本執(zhí)行之后, 在事件循環(huán)timers階段之前, 而setTimeout則是timers階段執(zhí)行.

所以這里優(yōu)先級(jí)是nextTick高于setTimeout.

剛好寫了一篇 Node.js的事件循環(huán)機(jī)制的文章, 有興趣可以讀一讀. 有閱讀疑問都可以提出來.
理解事件循環(huán)機(jī)制

2017年5月10日 11:23
編輯回答
久舊酒

牽扯到了js的單線程運(yùn)行機(jī)制,因?yàn)闄C(jī)制規(guī)定的原因,所以簡(jiǎn)單粗暴的理解為:
1、setTimeout和setInterval在指定的運(yùn)行時(shí)間到了后會(huì)查看本輪event loop是否執(zhí)行完畢;
2、如果完畢就執(zhí)行其中的回調(diào),沒有則會(huì)被移出本輪event loop放到下一輪進(jìn)行判斷,而process.nextTick與promise則會(huì)在本輪event loop結(jié)束后立即執(zhí)行;
3、所以setTimeout代碼書寫在前面或者后面并不會(huì)對(duì)process.nextTick的執(zhí)行產(chǎn)生影響,因?yàn)樗褪莾?yōu)先級(jí)最低的(個(gè)人理解);

如果對(duì)其中的原因感興趣可以去網(wǎng)上查閱js運(yùn)行機(jī)制和event loop的相關(guān)資料

2018年6月28日 23:36