JavaScript事件驅動機制&定時器機制

在瀏覽器中,事件做爲一個極爲重要的機制,給予JavaScript響應用戶操做與DOM變化的能力。在NodeJS中。異步事件驅動模型則是提升併發能力的基礎。javascript

1、程序怎樣響應事件

程序響應外部的事件有兩種方式:

1. 中斷

操做系統處理鍵盤等硬件輸入就是經過中斷來進行的。這個方式的優勢是即便沒有多線程,咱們也可以放心地運行咱們的代碼,CPU收到中斷信號以後本身主動地轉去運行對應的中斷處理程序,處理完畢後會恢復原來的代碼的運行環境繼續運行。java

這樣的方式需要硬件的支持。通常來講都會被操做系統封裝起來。瀏覽器

2. 輪詢

循環檢測是否有事件發生,假設有就去運行對應的處理程序。這在底層和上層的開發中都有應用。

輪詢方式的一個缺點就是:假設在主線程的消息循環裏進行耗時操做。程序就沒法及時響應新的消息。多線程

2、JavaScript中定時器功能的特色

不論是Node仍是瀏覽器中,都有setTimeout和setInterval這兩個定時器函數。並且其工做特色基本一樣。併發

JavaScript中的定時器並不一樣於計算機底層的定時中斷。異步

中斷到來時,當前運行代碼會被打斷。轉去運行定時中斷處理函數。函數

而JavaScript的定時器到時,假設當前運行線程沒有正在運行的代碼。則運行對應的回調函數;假設當前有代碼在運行中,JavaScript引擎既不會中斷當前代碼轉去運行回調,也不會開新的線程運行回調,而是當前代碼運行完成以後纔去處理。高併發

console.time("setTimoutLabel");	//標記時間開始
setTimeout(function() {
	console.timeEnd("setTimoutLabel");	//標記時間結束
}, 100);
for (var i = 0; i < 100000; i++) { }
 
 

運行上面的代碼。可以看到終於輸出的時間並不是100ms左右,而是數秒。post

這說明在循環完畢以前,定時回調函數確實沒有被運行。而是推遲到了循環結束。實際上在JavaScript代碼運行中,全部的事件都沒法獲得處理,必須等到當前代碼全部完畢,才幹去處理新的事件。這就是爲何在瀏覽器中運行耗時JavaScript代碼時,瀏覽器會失去響應。spa

3、定時器的工做原理

1. javascript引擎僅僅有一個線程,迫使異步事件僅僅能增長隊列去等待運行。

2. 在運行異步代碼的時候,假設定時器被正在運行的代碼堵塞了,它將會進入隊列的尾部去等待運行直到下一次可能運行的時間出現(可能超過設定的延時時間)。setTimeout 和setInterval 是有着本質差異的:setTimeout 這段代碼會在每次回調函數運行以後至少需要延時「指定延遲毫秒值」再去執行(多是不少其它,但是不會少)。但是setInterval會每隔「指定延遲毫秒值」就去嘗試運行一次回調函數。不管上一個回調函數是否是還在運行。

相關文章
相關標籤/搜索