最近我一直在研究 Web Worker,這是一份全面的指南,涵蓋了開始使用 Web Worker 所需了解的所有內容。
如果您想跳過閱讀部落格並查看程式碼,這裡是包含所有程式碼片段的 github 儲存庫。
Github Web Worker 儲存庫
所以,促使我探索 Web Workers 的原因是,在我建立的平台中,一項計算繁重的任務會阻塞 UI。
所以我想,『嗯,好吧,我該如何讓它不阻塞 UI』?我是否應該使用 setTimeout 來確保主線程中的所有程式碼都已執行完畢,然後才能運行計算量大的任務?
所以這是一個誤解-使用setTimeout並不代表UI不會被阻塞。是的,主執行緒上的所有內容都會在 setTimeout 回呼運行之前執行,但是,當該回呼從巨集任務佇列中彈出時,它會在主執行緒本身中運行,從而使 UI 無回應。
要了解更多有關 setTimeout 如何運作的信息,請參考一些參考資料 —
JavaScript 本質上是一種“單執行緒語言”,但是 Web Worker 使我們能夠在單獨的執行緒中運行計算量大的程式碼。
在開始之前,有幾件事要注意 -
const worker = new Worker("./worker.js")
注意:worker.js 不是一個模組,不能使用 import 語句。然而。 :')
要將worker.js當作模組,請在建構子的選項中指定type: module。
const worker = new Worker("./worker.js")
const worker = new Worker('./worker.js', { type: 'module' })
把它們放在一起
現在,讓我們看看整合 Web Worker 後我們的程式碼是什麼樣子。
主執行緒程式碼:
worker.terminate()
工作執行緒程式碼:
// ... function workerFunction() { // Don't spin up a new worker instance if the process has already been started. if (statusElement.textContent !== PROCESS_STATUS.PROCESSING && window.Worker) { const worker = new Worker('./worker.js', { type: 'module' }) // Sending 10000000000000 to the web worker worker.postMessage(10000000000000) statusElement.textContent = PROCESS_STATUS.PROCESSING // This piece of code is executed after worker finishes its task and returns data. worker.onmessage = function (event) { statusElement.textContent = event.data } } } // ...
結果:
當我們執行應用程式時,您會注意到執行計算量大的任務時不會阻塞 UI。
Comlink 是一個小型庫(1.1kB),它消除了思考 postMessage 邏輯的心理障礙。
在更抽象的層面上,它是 postMessage 和 ES6 代理程式的 RPC 實作。
我使用 Comlink 的一個具體原因是我無法使用純 JavaScript 將函數從主執行緒傳遞到工作執行緒。使用 Comlink 的代理,我能夠輕鬆地將回呼函數從主執行緒傳遞到工作執行緒。 [參考此部分]
要開始在專案中使用 comlink,請安裝庫
const worker = new Worker("./worker.js")
要開始使用這個函式庫,我們需要了解以下這些方法 -
Comlink.wrap(端點)
const worker = new Worker('./worker.js', { type: 'module' })
Comlink.expose(值、端點?、allowedOrigins?)
worker.terminate()
延伸閱讀
以上是開始之前您需要了解的有關 Web Worker 的所有資訊。的詳細內容。更多資訊請關注PHP中文網其他相關文章!