JS線程機制與事件機制


JS線程機制與事件機制

1.進程與線程

(1).定義:

  • 進程:程序的一次執行,它占有一片獨有的內存空間

  • CPU的基本調度單位,是程序執行的一個完整的流程

(2).進程與線程的關聯

  • 一個進程一般至少有一個運行的線程:主線程

  • 一個進程可以運行多個線程

  • 一個進程內的數據可以供其中的多個線程共享

  • 多個線程之間的數據是不能直接共享的

(3).瀏覽器基本上是多進程的

2.瀏覽器內核

(1).定義:支持瀏覽器運行的最核心的程序

(2).不同的瀏覽器運行的內核不同

  • Chrome,Safari:webkit

  • firefox:Gecko

  • IE:Trident

  • 國內瀏覽器360等:Trident + webkit

(3).內核組成的模塊:

  • html,css文檔解析模塊:負責頁面文本的解析

  • dom/css模塊: 負責dom/css在內存中的相關處理

  • 布局和渲染模塊:負責頁面的布局和效果的繪制

  • 定時器模塊:負責定時器的管理

  • 網絡請求模塊:負責服務器請求(Ajax)

  • 事件響應模塊:負責事件的管理

3.定時器

(1)分類:

  • 循環定時器:不關閉一直執行

  • 延時定時器:一定時間后才執行,只執行一次

(2)循環定時器:setInterval

 1     var i = 0;
 2     //獲得定時器句柄
 3     var intervalId = setInterval(function(){
 4       if (i >= 5) {
 5         //清除定時器
 6         clearInterval(intervalId);
 7       }
 8       console.log(Date.now());
 9       i++;
10     },1000);

(3)延時定時器:

1     setTimeout(function(){
2       console.log("----");
3     },2000);

4.JS是單進程的

(1)證明:

  • 使用setTimeout()回調函數在主線程運行

  • 定時器回調函數只有在運行棧中的代碼全部執行完畢后才可能執行

(2)為什么js要使用單線程模式:

  作為瀏覽器的腳本語言主要目的是和用戶交互,以及操作DOM,單線程會避免復雜的同步問題

(3)代碼分類:

  • 初始化代碼

  • 回調代碼

(4)JS引擎執行代碼的基本流程

  1. 先執行初始化代碼:包括一些特別的代碼:

    • 設定定時器

    • 綁定監聽

    • 發送Ajax請求

  2. 在某一時刻執行回調代碼

5.事件循環模型

執行流程:

1.同步任務加載執行

初始化代碼:綁定監聽,設置定時器,發送ajax請求

2.異步任務交給時間管理模塊

3.管理模塊監聽異步任務是否滿足條件,如果滿足條件就會將對應的任務放入callback queue中

4.主線程同步任務執行完成后通過event loop(事件輪詢機制)詢問callback queue

  • 有可執行的回調函數,就將回調函數放入主線程中執行

  • 如果沒有待會再來詢問

6.Web Workers:(需要開啟服務器)

(1)提供了js分線程實現

(2)相關API:

  • Worker:構造函數,加載分線程執行的js文件

  • Worker.prototype.onmessage:用於接收另一個線程的回調函數

  • Worker.prototype.postMessage:向另一個線程發送信息

(3)不足:

  • 不能操作DOM(不能更新UI)

  • 不能跨域加載JS

  • 不是每一個瀏覽器都支持這個新特性

(4)代碼:

在主線程html中編寫

 1 <input type="text" id="number" value="30">
 2 <button id="btn">計算斐波那契數</button>
 3 <script type="text/javascript">
 4 
 5 
 6 
 7 document.getElementById("btn").onclick = function(){
 8   var value = document.getElementById("number").value;
 9 
10   //獲得分線程
11   var worker = new Worker("./work.js");
12 
13   //發送給分線程數據
14   worker.postMessage(value);
15   //接收分線程數據
16   worker.onmessage = function(event){
17     console.log(event.data);
18   }
19 
20 }
21 </script>

在同一級目錄下work.js

 1 function fibonacci(num){
 2     return num > 2 ? fibonacci(num - 1) + fibonacci(num - 2) : 1;
 3 }
 4 
 5 var onmessage = function(event){
 6     console.log("分線程監視....");
 7 
 8     //獲取主線程發送過來的數據
 9     var data = event.data;
10 
11     //分線程處理數據
12     data = fibonacci(data);
13 
14     //返回數據給主線程
15     postMessage(data);
16 };

執行結果:

  不會卡住主進程界面,大批量計算在分線程中執行。

 


免責聲明!

本站轉載的文章為個人學習借鑒使用,本站對版權不負任何法律責任。如果侵犯了您的隱私權益,請聯系本站郵箱yoyou2525@163.com刪除。



 
粵ICP備18138465號   © 2018-2025 CODEPRJ.COM