javascript編程單執行緒之同步模式

javascript編程單執行緒之同步模式

主流的js 環境都是單執行緒嗎模式執行js 程式碼, js採用為單執行緒的原因與最開始設計初衷有關,最早是運行在瀏覽器端的腳本語言,目的是為了實現頁面上的動態交互,實現頁面交互的核心就是dom操作,這也就決定了js必須使用單執行緒的模式來處理,不然就會造成嚴重的執行緒同步問題。如果js多個執行緒同時修改dom元素,此時瀏覽器就無法明確以那個執行緒的結果為準,為了避免這種執行緒同步問題,所以從一開始js就被設置成了單執行緒模式工作。這裡所說的單執行緒指的是javascript執行環境中負責執行程式碼的執行緒只有一個

可以想像成只有一個人來執行任務,一個人一次只能執行一個任務,如果有多個任務就需要排隊依次去完成。這種模式最大的優點是更安全更簡單,缺點也很明顯,遇到某一個特別耗時的任務後面的任務就需要等這個任務的結束,這也就導致整個程式的執行的拖延,出現假死的情況。

  • 優點:更安全、更簡單
  • 耗時任務會出現程式假死的情況

為了結局耗時任務的問題,javscript 把 任務的執行分了兩種模式,分別是

  • 同步模式(Synchoronous)
  • 非同步模式(Asynchronous)

js.exec

同步模式Synchoronous

程式碼依次執行,後一個任務要等待前一個任務執行完成,同步執行比較簡單,程式碼的執行順序就是程式碼的順序。單執行緒大部分都是同步模式。

Console 是輸出的列印,Call stack 是執行棧

開始執行 js 會把我們的整體的程式碼載入進來並放到一個匿名函數裡面執行,然後逐行開始執行,

第一行 執行會把 console.log('global begin') 壓入調用棧中,控制台列印global begin 執行結束,彈出調用棧

接下來是兩個函數的聲明,函數的聲明不會產生調用所以接著往下執行

接下來是一個foo 函數的調用,會把 foo壓入調用棧,foo 函數列印了一個消息,接著執行了 bar 函數,bar 函數也會被放入執行棧中,bar函數執行過程中又列印了一次,bar執行完畢彈出調用棧,緊接著 foo 函數也執行結束,彈出調用棧

最後列印了一個消息,也是一樣的壓棧,整體程式碼執行完,執行棧就會被清空掉

js.aync.exec

這種排隊執行的機制下某行程式碼執行時間過長,後面的任務就會被延遲。我們把這種延遲稱為阻塞,這種阻塞對於用戶而言會有頁面卡頓或者叫卡死,所以需要非同步模式來解決程式中無法避免的耗時操作,比如ajax操作,或者nodejs中的大文件讀寫

更多內容微信公眾號搜索充饑的泡飯
小程式搜一搜開水泡飯的部落格