JavaScript Web Workers
JavaScript 本質上是一門「單執行緒」(Single-threaded) 的語言,這意謂著在瀏覽器中所有的程式碼都在同一個執行緒(主執行緒)上執行。
如果你的網頁需要進行非常大量的計算(例如:圖片過濾、大數據分析、複雜的加密運算等),主執行緒就會被阻塞,導致網頁畫面凍結、使用者無法點擊任何按鈕,這就是所謂的「卡頓」。
Web Workers 的出現,就是為了讓 JavaScript 也能在背景執行緒中運行任務,而不干擾主執行緒的 UI 渲染。
Web Workers 的特點
- 獨立執行緒: Worker 在完全獨立於主執行緒的環境中執行。
- 不阻塞 UI: 即使 Worker 正在進行耗時運算,使用者依然可以流暢地操作網頁。
- 無 DOM 存取權: 為了安全性與平行處理的一致性,Worker 內部無法直接存取範 DOM、window 或 document。
- 透過訊息通訊: 主執行緒與 Worker 之間透過
postMessage()發送訊息,並透過onmessage接收訊息。
基本用法
建立 Worker 檔案 (worker.js)
首先,我們將耗時的邏輯放在一個獨立的檔案中:
// worker.js
self.onmessage = function (e) {
console.log('Worker: 收到主執行緒訊息');
const num = e.data;
// 模擬繁重運算
const result = fibonacci(num);
console.log('Worker: 運算結束,傳回結果');
self.postMessage(result);
};
function fibonacci(n) {
if (n <= 1) return n;
return fibonacci(n - 1) + fibonacci(n - 2);
}
在主程式中啟動 Worker
// main.js
if (window.Worker) {
const myWorker = new Worker('worker.js');
// 發送資料給 Worker
myWorker.postMessage(40);
// 接收來自 Worker 的結果
myWorker.onmessage = function (e) {
console.log('主執行緒: 收到 Worker 回傳結果 ' + e.data);
};
myWorker.onerror = function (error) {
console.log('Worker 發生錯誤: ' + error.message);
};
}
什麼時候該用 Web Workers?
並非所有任務都需要 Worker,因為建立 Worker 本身也有開銷。適合使用的場景包括:
- 大量數值計算: 像是加密、解密、物理引擎模擬。
- 大數據排序與過濾: 當前端需要處理數萬條資料時。
- 圖片與影片處理: 例如即時套用圖片濾鏡。
總結
Web Workers 是開發具有流暢體驗的現代 Web 應用不可或缺的技術。當你發現某個函式執行超過 100ms 導致網頁有明顯延遲時,將該邏輯移往 Web Worker 就是通往 2025 高效能網頁的最佳實踐。