web前端渡一大師課 01 事件循環

一. 瀏覽器的進程模型?

1.何為進程?

程序運行需要有它自己專屬的內存空間,可以把這塊內存空間簡單理解為進程?

每個應用至少有一個進程,進程之間相互獨立,即使要通信,也需要雙方同意??

2.何為線程?

有了進程后,就可以運行程序的代碼了,運行代碼的"人",稱之為"線程",一個進程至少有一個線程,所以在進程開啟后會自動創建一個線程來運行代碼,該線程成為主線程. 如果程序需要同時執行多塊代碼,主線程就會啟動更多的線程來執行代碼,所以一個進程中可以包含多個線程

3. 瀏覽器有哪些進程和線程?

瀏覽器是一個多進程多線程的應用程序

瀏覽器內部工作及其復雜?

為了避免相互影響,為了減少連環崩潰的幾率,當啟動瀏覽器后,它會自動啟動多個線程?

可以在瀏覽器的任務管理器中查看當前的所有進程

? 其中,最主要的進程有:?

1. 瀏覽器進程:?

? ? ?主要負責界面顯示,用戶交互,子進程管理等,瀏覽器進程內部會啟動多個線程處理不同的任務

2. 網絡進程

? ? 負責加載網絡資源,網絡進程內部會啟動多個線程來處理不同的網絡任務?

3.渲染進程(本節課重點講解的過程)

? ? 渲染進程啟動后,會開啟一個渲染主線程,主線程負責執行HTML,CSS,JS代碼.默認情況下,瀏覽器? ? ? 會為每個標簽頁開啟一個新的渲染進程,以保證不同的標簽頁之間不相互影響

二.渲染主線程是如何工作的?

1.渲染主線程是瀏覽器中最繁忙的線程,需要它處理的任務包括但不限于:?

  • 解析 HTML?
  • 解析 CSS
  • 計算樣式
  • 布局
  • 處理圖層
  • 每秒把頁面畫 60 次
  • 執行全局 JS 代碼
  • 執行時間處理函數?
  • 執行計時器的回調函數?
  • ......

要處理這么多的任務,主線程遇到了一個前所 未有的難題: 如何調度任務?

比如:?

  • 我正在執行一個JS函數,執行到一半的時候用戶點擊了按鈕,我該立即去執行點擊事件的處理函數嗎?
  • 我正在執行一個JS函數,執行到一半的時候某個計時器到達了時間,我該立即去執行它的回調嗎?
  • 瀏覽器進程通知我"用戶點擊了按鈕",與此同時,某個計時器也到達了時間,我應該處理哪一個呢??

渲染主線程相處了一個絕妙的主意來處理這個問題: 排隊?

1.在最開始的時候,渲染主線程會進入一個無線循環?
2. 每一次循環會檢查消息隊列中是否有任務存在,如果有,就取出第一個任務執行,執行完一個進入下一次循環; 如果沒有,則進入休眠狀態?
3.其他所有線程(包括其他進程的線程)可以隨時向消息隊列添加任務,新任務會加到消息隊列的末尾,在添加新任務時,如果主線程是休眠狀態,則會將其喚醒以繼續循環拿去任務?

這樣一來,就可以讓每個任務有條不紊的,持續的進行下去了?

整個過程,被稱之為事件循環(消息循環)

三. 若干解釋?

1.何為異步?

代碼在執行過程中,會遇到 一些無法立即處理的任務,比如:??

  • 計時完成后需要執行的任務 --- setTimeout,setInterval
  • 網絡通信完成后需要執行的任務 -- XHR,Fetch?
  • 用戶操作后需要執行的任務 -- addEventListener?

如果讓渲染主線程等待這些任務的時機達到,就會導致瀏覽器[卡死 ]

渲染主線程承擔這極其重要的工作,無論如何都不能阻塞!

因此,瀏覽器選擇異步來解決這個問題

使用異步的方式,渲染主線程永不阻塞

總結:? 單線程是異步產生的原因,事件循環是異步的實現方式?

2.面試題: 如何理解JS的異步?

JS是一門單線程的語言,這是因為它運行在瀏覽器的渲染主線程中,而渲染主線程只有一個,渲染主線程承擔著諸多的工作,渲染頁面,執行JS都在其中運行

如果使用同步的方式,就極有可能導致主線程產生阻塞,從而導致消息隊列中的很多其他任務無法得到執行,這樣一來,一方面會導致繁忙的主線程白白的消耗時間,另一方面導致頁面無法及時更新,給用戶造成卡死現象.?

所以瀏覽器采用異步的方式來避免,具體做法是當某些任務發生時,比如計時器,網絡,事件監聽,主線程將任務交給其他線程去處理,自身立即結束任務的執行,轉而執行后續代碼,當其他線程完成時,將事先傳遞的回調函數包裝成任務,加入到消息隊列的末尾排隊,等待主線程調度執行

在這種異步模式下,瀏覽器永不阻塞,從而最大限度的保證了單線程的流暢運行?

?3.JS為何會阻礙渲染?

<!DOCTYPE html>
<html lang="zh-CN"><head><meta charset="UTF-8"><meta name="viewport" content="width=device-width, initial-scale=1.0"><title>Demo Page</title>
</head><body><h1 id="mainHeading">Mr.Yuan is awesome!</h1><button id="changeButton">change</button><script>// 獲取DOM元素var h1 = document.querySelector('h1');var btn = document.querySelector('button');// 死循環指定的時間function delay(duration) {// 獲取當前時間戳var start = Date.now();// 循環直到指定的時間過去while (Date.now() - start < duration) { }}// 按鈕點擊事件處理btn.onclick = function () {h1.textContent = '袁老師很帥!';delay(3000); // 延遲3秒(同步阻塞)};</script>
</body></html>
問題: 點擊按鈕后會發什么?

1. 即使DOM更新(肉眼不可見)

代碼執行: h1.trextContent='袁老師很帥!'

  • js會立即修改內存中的DOM樹,將<h1>的內容更改?
  • 但此時頁面尚未重新渲染,用戶還看不到變化(可通過console.log(h1.texctContent)驗證值已改變)
2. 主線程被死循環阻塞(3秒卡頓)
  • 代碼執行: deleay(3000)
  • 現象

    1. 瀏覽器主線程被while循環完全占用3秒?

    2. 期間頁面完全凍結: 所有交互(點擊/滾動),動畫,其他腳本執行均無響應
3. 3秒后渲染生效(突然變化)

時間點:delay(3000)執行完畢?

  • 主線程恢復控線狀態
  • 瀏覽器出發渲染管線
  • 用戶最終看到<h1>內容變為"袁老師很帥"

4.任務有優先級嗎?

任務沒有優先級,在消息隊列中先進先出

消息隊列是有優先級的?

根據W3C的最新解釋:?

  • 每個任務都有一個任務類型,同一個類型的任務必須在一個隊列,不同類型的任務可以分屬于不同的隊列,在一次時間循環中,瀏覽器可以根據實際情況從不同隊列中取出任務執行
  • 瀏覽器必須準備好一個微隊列,微隊列中的任務優先所有其他任務執行

隨著瀏覽器的復雜度急劇提升,W3C 不再使用宏隊列的說法?

?在目前chrome的實現中,至少包含了下面的隊列:??

  • 延時隊列: 用于存放計時器到達后的回調任務,優先級[中]
  • 交互隊列: 用于存放用戶操作后產生的事件處理任務,優先級 [高]
  • 微隊列: 用戶存放需要最快執行的任務,優先級[最高]

添加任務到微隊列的主要方式是使用Promise,MutationObsever?

例如:?

//立即把一個函數添加到微隊列

Promise.resolve().then(函數)

瀏覽器還有很多其他的隊列,由于和我們開發關系不大,不作考慮?

事件問題

1.
setTimeout(function () {console.log(1);
}, 0);console.log(2);

1. 一開始執行全局JS,然后其他線程開始計時,計時過后,開始排隊?

2.

這里是有錯誤,應該是在延時隊列,后面有糾正?

3. 等全局js執行完之后, 把延時隊列的fn 放到主線程

4. 輸出 2 1

2.
function delay(duration) {var start = Date.now();while (Date.now() - start < duration) {}
}setTimeout(function () {console.log(1);
}, 0);console.log(2);

先輸出2 ,等待1s 輸出1??

3.

1

setTimeout(function () {console.log(1);
}, 0);Promise.resolve().then(function () {console.log(2);
});console.log(3);

2.
3. 輸出 3 2 1

首先執行同步代碼 ,然后檢查并執行所有微任務(Promise回調),輸出2

最后執行延時隊列中的回調(setTimeout),輸出1?

4.?


function a() {console.log(1);Promise.resolve().then(function () {console.log(2);});
}setTimeout(function () {console.log(3);Promise.resolve().then(a);
}, 0);Promise.resolve().then(function () {console.log(4);
});console.log(5);
1.?

1. 把輸出3的函數,和輸出4的函數,放入相對應的隊列中?

2. 全局執行完畢,先輸出5 ,在執行fn4 輸出4,在執行fn3 輸出3?

3. 執行fn3,把函數a放到微隊列

4. fn3執行完之后,把a放到渲染主線程?

5., a執行完之后輸出1吧輸出2的函數放到微隊列,然后輸出2

6. 最后輸出54312
面試題: 闡述一下JS的事件循環

參考答案:??

事件循環又叫做消息循環,是瀏覽器渲染主線程的工作方式.?

在Chrome的源碼中,它開啟一個不會結束的for循環,每次循環從消息隊列中取出第一個任務執行,而其他線程只需要在適合的時候將任務加入到隊列末尾即可.

過去吧消息隊列簡單分為宏任務和微隊列,這種說法目前已無法滿足復雜的瀏覽器環境,取而代之的是一種更加靈活多變的處理方式

根據W3C官方的解釋,每個任務有不同的類型,同類型的任務必須在同一個隊列,不同的任務可以屬于不同的隊列,不同任務隊列有不同的優先級,在一次事件循環中,由瀏覽器自行決定取哪一個隊列的任務,但瀏覽器必須有一個微隊列,微隊列的任務一定具有最高的優先級,必須優先調度執行

面試題: JS中的計時器能做到精確計時嗎?為什么?

參考答案:?

不行,因為:?

1. 計算機硬件沒有原子鐘,無法做到精確計時?

2. 操作系統的計時函數本身就有少量偏差,由于JS的計時器最終調用的是操作系統的函數,也就攜帶了這些偏差?

3. 按照W3C的標準,瀏覽器實現的計時器時,如果嵌套層級超過5層,則會帶有4毫秒的最少時間,這樣在計時時間少于4毫秒時又帶來了偏差

4.? 受事件循環的影響,計時器的回調函數只能在主線程空閑時運行,因此又帶來的偏差?

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/diannao/91226.shtml
繁體地址,請注明出處:http://hk.pswp.cn/diannao/91226.shtml
英文地址,請注明出處:http://en.pswp.cn/diannao/91226.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

linux網絡存儲——freeNAS的安裝配置

一、前言 freeNAS 是一款基于 FreeBSD 的開源網絡存儲操作系統&#xff0c;支持文件共享&#xff08;如 SMB/CIFS、NFS、AFP&#xff09;、數據備份、虛擬化存儲等功能。同時FreeNAS開源優勢明顯&#xff0c;代碼開放可自主定制&#xff0c;能滿足多樣需求。支持多種協議…

深度學習圖像分類數據集—七種樹葉識別分類

該數據集為圖像分類數據集&#xff0c;適用于ResNet、VGG等卷積神經網絡&#xff0c;SENet、CBAM等注意力機制相關算法&#xff0c;Vision Transformer等Transformer相關算法。 數據集信息介紹&#xff1a;七種樹葉識別分類&#xff1a;[冬青葉, 楊樹葉, 柳葉, 梧桐葉, 石楠葉,…

c++圖形題練習程序

一.練習題背景 這題是作者再一家公司實習的時候&#xff0c;實習期間的一個考核題目&#xff0c;感覺還是比較有價值的。希望能給還在努力的學弟學妹們一些啟發。 題目大致就是要求用繼承和多態來實現圓、三角形和長方形的面積和周長求解。這步的大致思路是這樣的&#xff0c;你…

【論文閱讀 | PR 2024 |ITFuse:一種用于紅外與可見光圖像融合的交互式 Transformer】

論文閱讀 | PR 2024 |ITFuse&#xff1a;一種用于紅外與可見光圖像融合的交互式 Transformer1.摘要&&引言2.方法2.1 問題表述2.2 框架概述2.3 特征交互模塊2.3.1 共同特征提取分支&#xff08;IcI_{c}Ic? 分支&#xff09;2.3.2 獨特特征提取分支&#xff08;I1I_{1}I…

【Qt】 設計模式

在Qt應用程序開發中&#xff0c;結合數據庫操作、通信、界面邏輯和顯示等功能&#xff0c;以下是常用的設計模式及其典型應用場景&#xff1a; 一、MVC/MVVM&#xff08;模型-視圖-控制器/視圖模型&#xff09; 作用&#xff1a;分離數據&#xff08;模型&#xff09;、界面&am…

【HarmonyOS】ArkUI-X 跨平臺框架入門詳解(一)

【HarmonyOS】ArkUI-X 跨平臺框架入門詳解&#xff08;一&#xff09; 一、前言 1、ArkUI-X框架是什么&#xff1f; ArkUI-X是在ArkUI開發框架的基礎上&#xff0c;進行擴展。支持多個OS平臺&#xff0c;目前支持OpenHarmony、HarmonyOS、Android、 iOS。2、ArkUI-X目前的能力現…

開發者進化論:駕馭AI,開啟軟件工程新紀元

導語&#xff1a;人工智能&#xff08;AI&#xff09;的浪潮&#xff0c;特別是以大型語言模型&#xff08;LLM&#xff09;為代表的生成式AI&#xff0c;正以前所未有的力量&#xff0c;深刻地重塑著軟件開發的傳統疆域。我們正處在一個關鍵的轉折點——產業的重心正從模型的“…

智慧水務平臺,智慧水務,惠及民生,提升水務管理效率與服務質量

平升電子智慧水務平臺支持海量物聯網數據接入實現供水全流程信息化&#xff0c;深度邏輯運算自動控制實現供水調度智慧化&#xff0c;融入管網地理信息系統實現測點數據時空化&#xff0c;數字孿生實現水廠各工藝環節運行情況可視化&#xff0c;多角度統計分析實現水務運營管理…

【Unity基礎】Unity中元素的層級排序

在Unity中&#xff0c;控制元素的層級排序&#xff08;渲染順序&#xff09;是確保場景正確顯示的關鍵。以下是常見的層級排序方式及其適用場景&#xff1a;1. 通過GameObject的層級順序&#xff08;Sorting Layer/Order in Layer&#xff09; 適用對象&#xff1a;2D精靈&…

梁的振動特征函數分析2

問題7&#xff1a;左端固定、右端自由梁的振動分析 考慮梁的振動方程&#xff1a; uttKuxxxx0,0<x<l,K>0 u_{tt} K u_{xxxx} 0, \quad 0 < x < l, \quad K > 0 utt?Kuxxxx?0,0<x<l,K>0 邊界條件&#xff1a; 左端固定&#xff08;位移和斜率為零…

AI問答-Token:在人工智能領域,Token 是模型處理文本的核心單元 / 最小可處理片段

一、在人工智能領域&#xff0c;Token 是模型處理文本的核心單元&#xff0c;可理解為文本的“最小可處理片段”二、表格理解類別詳細說明基本定義Token 是模型處理文本的最小語義或語法單位&#xff0c;可以是單詞、子詞、字符、標點符號或特殊符號。例如&#xff1a;- 單詞級…

讀取ubuntu的磁盤分區表與超級塊

1.讀取磁盤分區表sudo fdisk -l /dev/sda2.計算偏移量分區起始偏移 4096 512 2097152 字節 超級塊位置 2097152 1024 2098176字節3.快速驗證&#xff08;直接檢查魔數 53 &#xff09;# 檢查偏移 2,098,176 處是否有 EXT4 魔數 sudo dd if/dev/sda bs1 count2 skip$((209…

科技馴服烈日狂沙:中東沙漠農場的光儲革命

作者 | 小葳 阿布扎比郊外的午后&#xff0c;沙漠灼熱、干旱難耐。 然而一座農場內&#xff0c;景象截然不同&#xff1a;蔬菜生機盎然&#xff0c;果實掛滿枝頭。農戶輕點手機&#xff0c;遠程調控著大棚內溫濕度&#xff1b;灌溉與施肥&#xff0c;則由系統自動精準執行。 這…

基于Chinese-CLIP與ChromaDB的中文圖像檢索功能實現

本文按“原理 → 代碼 → 講解”三層展開&#xff0c;讀者只需具備 Python 基礎即可跟隨完成一個可落地的以文搜圖應用。 一、整體思路 把圖片和文字都轉成固定長度的向量&#xff08;768 維&#xff09;。把圖片向量提前存入向量數據庫。查詢時把文字轉成向量&#xff0c;再找…

Pandas 的 Index 與 SQL Index 的對比

一、Pandas 的 Index&#xff08;索引&#xff09;是什么&#xff1f;Pandas 的 Index 就像是 Excel 表格的行號 列標題&#xff0c;或者書的目錄。核心作用&#xff1a;定位數據&#xff1a;就像 Excel 中用行號和列名定位單元格&#xff08;如 A1、B2&#xff09;&#xff0…

Rust指針選擇

Rust指針選擇&#xff1a; 1.優先使用引用&#xff1a;安全訪問數據 fn process(data: &[i32]) { /* ... */ }2.需要所有權轉移時用 Box fn create() -> Box<Data> { Box::new(Data::new()) }3.共享數據用 Rc/Arc // 單線程 let shared Rc::new(data);// 多線程 …

【實用IP查詢工具】IP數據云-IP地址查詢離線庫使用方案

IP數據云&#xff08;ipdatacloud.com&#xff09;深耕IP地址查詢技術&#xff0c;打造了覆蓋多場景、高精度的IP地址查詢離線庫&#xff0c;為不同行業客戶提供穩定、高效的本地化數據支持。 什么是IP 地址查詢 離線庫&#xff1f; IP地址查詢離線庫是將海量IP地址與對應的地…

UE5CameraShake參數詳解

使用CameraShakeBase藍圖中簡單調用和調試 使用 Play World Camera Shake 這個節點帶有震動衰減效果Epicenter是震動中心點 傳入Boss的位置 Inner Radius是 內部范圍 距離小于內部范圍時 , 全強度震動Outer Radius是 外部范圍 距離大于外部范圍時 , 就無震動Falloff 是衰…

java學習 day4 分布式鎖

P60分布式鎖誤刪線程標示和鎖中標示一致P61分布式鎖的原子性問題判斷鎖標示和釋放鎖不同時 造成誤刪P62Lua腳本P63java執行Lua腳本原子性P64redissionredisson框架P65redisson入門P66redisson可重入鎖原理和測試redisson可重入鎖P67鎖重試看門狗看到67 10min處&#xff0c;看不…

python+selenium UI自動化初探

在公司上班閑的沒事干&#xff0c;學點selenium 先安裝selenium pip install selenium出現報錯 Cannot uninstall certifi None ╰─> The packages contents are unknown: no RECORD file was found for certifi.hint: You might be able to recover from this via: pip in…