国产xxxx99真实实拍_久久不雅视频_高清韩国a级特黄毛片_嗯老师别我我受不了了小说

資訊專欄INFORMATION COLUMN

事件循環(huán)與任務(wù)隊列

SQC / 2233人閱讀

摘要:需要注意的是,定時器比較特殊,并沒有把回調(diào)函數(shù)掛在事件循環(huán)隊列中,它所做的就是設(shè)置一個定時器,當(dāng)定時器到時后,環(huán)境會把你的回調(diào)函數(shù)放在事件循環(huán)中,這樣,在未來某個時刻的會被取出執(zhí)行。

Author: bugall
Wechat: bugallF
Email: 769088641@qq.com
Github: https://github.com/bugall

一: 事件循環(huán)

雖然我們用Javascript總是可以實(shí)現(xiàn)一些異步代碼, 但是Javascript中真正的異步概念,但是直到ES6,Javascript才內(nèi)建了直接的異步概念。

對于原有Javascript引擎來說, 它只關(guān)心如何去執(zhí)行給定的代碼塊, 對于什么時候該執(zhí)行哪些代碼塊這個是引擎不關(guān)心的。引擎是依賴于宿主環(huán)境的,這里的宿主環(huán)境并不是指操作系統(tǒng)環(huán)境,因?yàn)椴煌钠脚_提供的“可執(zhí)行環(huán)境”不同。而宿主環(huán)境就是為了隔離代碼、語言與具體的平臺而提出的一個設(shè)計。比如web瀏覽器環(huán)境,Node.js這樣的工具等,所有的這些環(huán)境都有一個共同點(diǎn),它們都提供了一種機(jī)制來處理程序中多個代碼塊的執(zhí)行,且執(zhí)行每塊時調(diào)用Javascript引擎,這種機(jī)制被成為事件循環(huán)

換句話說,Javascript引擎本身并沒有時間的概念,只是一個按需執(zhí)行Javascript任意代碼片段的環(huán)境。“事件”的調(diào)度總是由包含它的環(huán)境進(jìn)行。

注意!!!,ES6后事件的管理方式有所改變。ES6本身解決的事件在哪里管理的問題,現(xiàn)在ES6精確指定了事件循環(huán)的工作細(xì)節(jié),這就 意味著技術(shù)上將其納如了Javascript引擎的勢力范圍,而不再由宿主環(huán)境管理,這個改變的一個主要原因是ES6中Promise的引入,這個技術(shù)要求事件循環(huán)隊列的調(diào)度運(yùn)行能夠直接進(jìn)行精細(xì)的控制

我們看下面的這段代碼:

function task() {
    console.log("Hello Word");
}
setTimeout(task, 1000);

如果你在代碼中設(shè)置一個計時器, 當(dāng)計時器到達(dá)指定的時間后執(zhí)行函數(shù)task, 當(dāng)Javascript引擎執(zhí)行到定時器的時候會通知宿主環(huán)境:“我要去做別的事情, 等1秒后就調(diào)用task函數(shù),注意:是調(diào)用而不是執(zhí)行)

我們用一段偽代碼實(shí)現(xiàn)一個簡單的事件循環(huán)

var eventList = [event1, event2, event3];
var event;
while(true) {
    if (eventList.length > 0 ) {
        event = eventList.pop();
    }
    run(event);
}

可以看到有一個用while循環(huán)實(shí)現(xiàn)的持續(xù)運(yùn)行的循環(huán),當(dāng)event1, event2, event3都取出被執(zhí)行一次后稱為一輪,循環(huán)的每一輪稱為一個tick,對于每一個tick而言,如果在隊列中有等待的事件,那么就會從隊列中取出下一個事件并執(zhí)行,這些事件就是我們代碼中寫的回調(diào)函數(shù)。

需要注意的是,定時器比較特殊,setTimeout(task, 1000)并沒有把回調(diào)函數(shù)掛在事件循環(huán)隊列中,它所做的就是設(shè)置一個定時器,當(dāng)定時器到時后,環(huán)境會把你的回調(diào)函數(shù)放在事件循環(huán)中,這樣,在未來某個時刻的tick會被取出執(zhí)行。

如果你的事件循環(huán)中已經(jīng)有很多項(xiàng)目后,定時器的回調(diào)就要被放到隊尾( 不支持搶占式 )等待被執(zhí)行,這也就是定時器不準(zhǔn)的原因。定時器的回調(diào)函數(shù)的執(zhí)行要根據(jù)時間隊列的狀態(tài)而定。
那么該如何去降低定時器誤差呢?

二:任務(wù)隊列

嚴(yán)格來說,定時器并不直接把回調(diào)函數(shù)直接插到事件循環(huán)隊列,定時器會在有機(jī)會的時候插入事件,對于連續(xù)的兩個setTimeout(..., 0)調(diào)用不能保證會嚴(yán)格按照調(diào)用順序處理,所以各種情況都會發(fā)生,比如定時器漂移,這類結(jié)果是不可預(yù)測的,在Node.js中可以用process.nextTick(...)。但是不能保證所有環(huán)境都能控制異步的順序。

在ES6中,在事件循環(huán)隊列上有個一個新的概念,那就是任務(wù)隊列,這個概念給大家?guī)淼淖畲笥绊懣赡芫褪?b>Promise的異步特性

任務(wù)隊列就是掛在時間循環(huán)隊列的每個tick之后的一個隊列,在事件循環(huán)的每個tick中,可能出現(xiàn)的異步動作不會導(dǎo)致一個完整的新事件添加到事件循環(huán)隊列中,而會在當(dāng)前tick的任務(wù)隊列末尾添加一個任務(wù)。
一個任務(wù)可能引起更多任務(wù)被添加到同一個隊列末尾,所以理論上說,任務(wù)循環(huán)可能無限循環(huán),無法轉(zhuǎn)移到下一個事件循環(huán)tick.

任務(wù)隊列的概念,那么怎么減少定時器的誤差?看代碼:

function task() {
    console.log("Hello Word");
}
setTimeout(task, 1000);

如果現(xiàn)在時間隊列中有100個等待被執(zhí)行的任務(wù),這時候task任務(wù)準(zhǔn)備插入到事件隊列。

沒有引入任務(wù)隊列前:
task會被插入到當(dāng)前事件循環(huán)隊列的末端,等待下次的tick被執(zhí)行,那么這就需要等到當(dāng)前的tick被執(zhí)行完,那么這時候的timer延時就決定于100個等待執(zhí)行的任務(wù)耗時。

引入任務(wù)隊列之后:
直接插入到當(dāng)前tick的任務(wù)隊列被執(zhí)行

文章版權(quán)歸作者所有,未經(jīng)允許請勿轉(zhuǎn)載,若此文章存在違規(guī)行為,您可以聯(lián)系管理員刪除。

轉(zhuǎn)載請注明本文地址:http://m.specialneedsforspecialkids.com/yun/86986.html

相關(guān)文章

  • JavaScript運(yùn)行機(jī)制和事件循環(huán)

    摘要:主線程不斷重復(fù)上面的三步,此過程也就是常說的事件循環(huán)。所以主線程代碼執(zhí)行時間過長,會阻塞事件循環(huán)的執(zhí)行。參考資料這一次,徹底弄懂執(zhí)行機(jī)制任務(wù)隊列的順序機(jī)制事件循環(huán)搞懂異步事件輪詢與中的事件循環(huán) 1. 說明 讀過本文章后,您能知道: JavaScript代碼在瀏覽器中的執(zhí)行機(jī)制和事件循環(huán) 面試中經(jīng)常遇到的代碼輸出順序問題 首先通過一段代碼來驗(yàn)證你是否了解代碼輸出順序,如果你不知道輸出...

    Ververica 評論0 收藏0
  • 今天,我明白了JS事件循環(huán)機(jī)制

    摘要:而這些隊列由的事件循環(huán)來搞定宏任務(wù)與微任務(wù),在最新標(biāo)準(zhǔn)中,它們被分別稱為與。我們梳理一下事件循環(huán)的執(zhí)行機(jī)制循環(huán)首先從宏任務(wù)開始,遇到,生成執(zhí)行上下文,開始進(jìn)入執(zhí)行棧,可執(zhí)行代碼入棧,依次執(zhí)行代碼,調(diào)用完成出棧。 寫在前面 js是一門單線程的編程語言,也就是說js在處理任務(wù)的時候,所有任務(wù)只能在一個線程上排隊被執(zhí)行,那如果某一個任務(wù)耗時比較長呢?總不能等到它執(zhí)行結(jié)束再去執(zhí)行下一個。所以在...

    maochunguang 評論0 收藏0
  • 總結(jié):JavaScript異步、事件循環(huán)消息隊列、微任務(wù)任務(wù)

    摘要:單線程異步非阻塞然后,這又牽扯到了事件循環(huán)消息隊列,還有微任務(wù)宏任務(wù)這些。此步的位置不確定某個時刻后,定時器觸發(fā)線程通知事件觸發(fā)線程,事件觸發(fā)線程將回調(diào)函數(shù)加入消息隊列隊尾,等待引擎線程執(zhí)行。 前言 Philip Roberts 在演講 great talk at JSConf on the event loop 中說:要是用一句話來形容 JavaScript,我可能會這樣: Java...

    qianfeng 評論0 收藏0
  • JavaScript單線程事件循環(huán)(Event Loop)那些事

    摘要:概述本篇主要介紹的運(yùn)行機(jī)制單線程事件循環(huán)結(jié)論先在中利用運(yùn)行至完成和非阻塞完成單線程下異步任務(wù)的處理就是先處理主模塊主線程上的同步任務(wù)再處理異步任務(wù)異步任務(wù)使用事件循環(huán)機(jī)制完成調(diào)度涉及的內(nèi)容有單線程事件循環(huán)同步執(zhí)行異步執(zhí)行定時器的事件循環(huán)開始 1.概述 本篇主要介紹JavaScript的運(yùn)行機(jī)制:單線程事件循環(huán)(Event Loop). 結(jié)論先: 在JavaScript中, 利用運(yùn)行至...

    Shisui 評論0 收藏0
  • 淺談不同環(huán)境下的JavaScript執(zhí)行機(jī)制 + 示例詳解

    摘要:如果沒有其他異步任務(wù)要處理比如到期的定時器,會一直停留在這個階段,等待請求返回結(jié)果。執(zhí)行的執(zhí)行事件關(guān)閉請求的,例如事件循環(huán)的每一次循環(huán)都需要依次經(jīng)過上述的階段。因此,才會早于執(zhí)行。 showImg(https://segmentfault.com/img/bVbnY76); 概念 同步任務(wù)(Synchronous) 在主線程上排隊執(zhí)行的任務(wù),只有前一個任務(wù)執(zhí)行完畢,才能執(zhí)行后一個任務(wù) ...

    wanghui 評論0 收藏0

發(fā)表評論

0條評論

最新活動
閱讀需要支付1元查看
<