Web Workers in JavaScript
Dit artikel legt uit wat Web Workers in JavaScript zijn.
YouTube Video
javascript-web-worker.html
1<!DOCTYPE html>
2<html lang="en">
3<head>
4 <meta charset="UTF-8">
5 <title>JavaScript & HTML</title>
6 <style>
7 * {
8 box-sizing: border-box;
9 }
10
11 body {
12 margin: 0;
13 padding: 1em;
14 padding-bottom: 10em;
15 font-family: 'Segoe UI', Tahoma, Geneva, Verdana, sans-serif;
16 background-color: #f7f9fc;
17 color: #333;
18 line-height: 1.6;
19 }
20
21 .container {
22 max-width: 800px;
23 margin: 0 auto;
24 padding: 1em;
25 background-color: #ffffff;
26 border: 1px solid #ccc;
27 border-radius: 10px;
28 box-shadow: 0 4px 12px rgba(0, 0, 0, 0.05);
29 }
30
31 .container-flex {
32 display: flex;
33 flex-wrap: wrap;
34 gap: 2em;
35 max-width: 1000px;
36 margin: 0 auto;
37 padding: 1em;
38 background-color: #ffffff;
39 border: 1px solid #ccc;
40 border-radius: 10px;
41 box-shadow: 0 4px 12px rgba(0, 0, 0, 0.05);
42 }
43
44 .left-column, .right-column {
45 flex: 1 1 200px;
46 min-width: 200px;
47 }
48
49 h1, h2 {
50 font-size: 1.2rem;
51 color: #007bff;
52 margin-top: 0.5em;
53 margin-bottom: 0.5em;
54 border-left: 5px solid #007bff;
55 padding-left: 0.6em;
56 background-color: #e9f2ff;
57 }
58
59 button {
60 display: block;
61 margin: 1em auto;
62 padding: 0.75em 1.5em;
63 font-size: 1rem;
64 background-color: #007bff;
65 color: white;
66 border: none;
67 border-radius: 6px;
68 cursor: pointer;
69 transition: background-color 0.3s ease;
70 }
71
72 button:hover {
73 background-color: #0056b3;
74 }
75
76 #output {
77 margin-top: 1em;
78 background-color: #1e1e1e;
79 color: #0f0;
80 padding: 1em;
81 border-radius: 8px;
82 min-height: 200px;
83 font-family: Consolas, monospace;
84 font-size: 0.95rem;
85 overflow-y: auto;
86 white-space: pre-wrap;
87 }
88
89 .highlight {
90 outline: 3px solid #ffc107; /* yellow border */
91 background-color: #fff8e1; /* soft yellow background */
92 transition: background-color 0.3s ease, outline 0.3s ease;
93 }
94
95 .active {
96 background-color: #28a745; /* green background */
97 color: #fff;
98 box-shadow: 0 0 10px rgba(40, 167, 69, 0.5);
99 transition: background-color 0.3s ease, box-shadow 0.3s ease;
100 }
101 </style>
102</head>
103<body>
104 <div class="container">
105 <h1>JavaScript Console</h1>
106 <button id="executeBtn">Execute</button>
107 <div id="output"></div>
108 </div>
109
110 <script>
111 // Override console.log to display messages in the #output element
112 (function () {
113 // Override console.log
114 const originalLog = console.log;
115 console.log = function (...args) {
116 originalLog.apply(console, args);
117 const message = document.createElement('div');
118 message.textContent = args.map(String).join(' ');
119 output.appendChild(message);
120 };
121
122 // Override console.error
123 const originalError = console.error;
124 console.error = function (...args) {
125 originalError.apply(console, args);
126 const message = document.createElement('div');
127 message.textContent = args.map(String).join(' ');
128 message.style.color = 'red'; // Color error messages red
129 output.appendChild(message);
130 };
131 })();
132
133 document.getElementById('executeBtn').addEventListener('click', () => {
134 // Prevent multiple loads
135 if (document.getElementById('externalScript')) return;
136
137 const script = document.createElement('script');
138 script.src = 'javascript-web-worker.js';
139 script.id = 'externalScript';
140 //script.onload = () => console.log('javascript-web-worker.js loaded and executed.');
141 //script.onerror = () => console.log('Failed to load javascript-web-worker.js.');
142 document.body.appendChild(script);
143 });
144 </script>
145</body>
146</html>
Web Worker
in JavaScript
Web Worker
in JavaScript is een mechanisme waarmee code in een aparte thread kan draaien, los van de hoofdthread. Hierdoor kunnen zware berekeningen en langdurige operaties asynchroon worden uitgevoerd, waardoor de hoofdthread niet wordt geblokkeerd. Door gebruik te maken van Web Worker
verbetert de responsiviteit van de gebruikersinterface en wordt de prestatie van de applicatie verbeterd.
Het basisgebruik van Web Worker
Laten we kijken naar het basisgebruik van Web Worker
.
Een nieuwe Web Worker
wordt aangemaakt door een JavaScript-bestand te specificeren.
1// worker.js (created as a separate file)
2onmessage = function(event) {
3 // Receive a message
4 const data = event.data;
5 // Perform heavy computation or processing
6 const result = data * 2;
7 // Return the result to the main thread
8 postMessage(result);
9};
1// Main thread (main.js)
2const worker = new Worker('worker.js');
3
4// Send a message to the worker
5worker.postMessage(10);
6
7// Receive a message from the worker
8worker.onmessage = function(event) {
9 console.log('Result from Worker: ', event.data); // Result: 20
10};
11
12// Error handling
13worker.onerror = function(error) {
14 console.error('Worker error: ', error);
15};
- Deze code demonstreert het basismechanisme waarbij een
Web Worker
wordt gebruikt om berekeningen aan te vragen vanaf de hoofdthread en het resultaat asynchroon te ontvangen. Er wordt10
als bericht naar deWeb Worker
gestuurd en20
als resultaatbericht ontvangen. De hoofdthread en deWeb Worker
communiceren door berichten te verzenden en te ontvangen om verwerkingsresultaten aan te vragen en te ontvangen.
Basisfuncties
Web Worker
biedt de volgende basisfuncties.
postMessage
enonmessage
Wordt gebruikt om berichten te versturen en te ontvangen tussen de hoofdthread en deWeb Worker
. Verzend gegevens metpostMessage
en ontvang deze metonmessage
.- Thread-onafhankelijkheid
Web Worker
werkt volledig onafhankelijk van de hoofdthread. Daarom kunnen variabelen en functies die in de hoofdthread zijn gedefinieerd niet worden benaderd. Benodigde gegevens moeten worden doorgegeven viapostMessage
. - Scriptimport
Om externe scripts te laden binnen een
Web Worker
, gebruik jeimportScripts()
.
1// mathUtils.js
2function double(n) {
3 return n * 2;
4}
1// worker.js
2importScripts('mathUtils.js');
3
4onmessage = function(event) {
5 const input = event.data;
6 const result = double(input); // mathUtils.jsの関数を使用
7 postMessage(result);
8};
1// Main thread (main.js)
2const worker = new Worker('worker.js');
3
4// Send a message to the worker
5worker.postMessage(10);
6
7// Receive a message from the worker
8worker.onmessage = function(event) {
9 console.log('Result from Worker: ', event.data); // Result: 20
10};
11
12// Error handling
13worker.onerror = function(error) {
14 console.error('Worker error: ', error);
15};
Als alternatief kun je ook import
gebruiken zoals hieronder getoond.
1// lib.js
2
3// Simulated CPU-intensive task
4export function doHeavyWork(n) {
5 return n * 2;
6}
1// worker.js
2import { doHeavyWork } from './lib.js';
3
4self.onmessage = (event) => {
5 const data = event.data;
6 const result = doHeavyWork(data);
7 self.postMessage(result);
8};
1// Main thread (main.js)
2const worker = new Worker('worker.js', { type: 'module' });
3
4// Send a message to the worker
5worker.postMessage(10);
6
7// Receive a message from the worker
8worker.onmessage = function(event) {
9 console.log('Result from Worker: ', event.data); // Result: 20
10};
11
12// Error handling
13worker.onerror = function(error) {
14 console.error('Worker error: ', error);
15};
- Door
type: 'module'
te specificeren als argument vannew Worker
, kun je de worker als een ES-module behandelen en deimport
-syntax gebruiken.
Verschillen tussen Web Worker
en async
-functies
Web Worker
Kenmerken
- Thread-isolatie
Web Worker
voert JavaScript-code uit in een aparte thread. Hierdoor kunnen zware berekeningen worden uitgevoerd zonder de hoofdthread (UI-thread) te blokkeren. - Gelijktijdige verwerking
Met
Web Worker
kunnen JavaScript-programma’s gelijktijdige verwerking uitvoeren in meerdere threads. - Berichtcommunicatie
De
Web Worker
en de hoofdthread delen geen data direct, maar wisselen berichten uit viapostMessage
enonmessage
. - Geen toegang tot UI
Web Worker
heeft geen toegang tot de DOM, dus kan de UI niet direct manipuleren.
Gebruiksscenario's
- Het is geschikt voor zware rekenprocessen zoals beeldverwerking, data-analyse en encryptie.
- Het kan worden gebruikt wanneer u de hoofdthread niet wilt blokkeren.
async
Kenmerken
- Vereenvoudigen van asynchrone verwerking
De
async
-functie is een syntaxis die asynchrone verwerking leesbaarder maakt, waarbij intern gebruik wordt gemaakt vanPromise
. - Enkele thread
Alle
async
-functies draaien op de hoofdthread. Daarom moet u methoden bedenken om te voorkomen dat de UI-thread wordt geblokkeerd. - Optimaal voor I/O-bewerkingen Het is geschikt voor asynchrone taken zoals netwerkcommunicatie en het lezen van bestanden, maar niet voor zware berekeningen.
Gebruiksscenario's
- Het is geschikt voor netwerkcommunicatie zoals API-aanroepen.
- Het is geschikt voor het lezen en schrijven van bestanden met behulp van browser-API's of Node.js.
Belangrijkste Verschillen
Kenmerken | Web Worker | async |
---|---|---|
Uitvoeringsomgeving | Aparte thread | Hoofdthread |
Doel | Parallelle verwerking, zware berekeningen ontlasten | Beknopte beschrijving van asynchrone operaties |
Toegang tot DOM | Niet mogelijk | Mogelijk |
Communicatiemethode | Berichtuitwisseling (bijv. postMessage ) |
Niet nodig (afgehandeld via directe functieaanroepen of await ) |
Gebruikssituaties | Tijdrovende berekeningen, data-analyse | I/O-operaties, API-aanroepen |
Wanneer Elke Te Gebruiken Is
Voor CPU-intensieve taken kun je Web Worker
gebruiken om de belasting van de hoofdthread te verminderen. Aan de andere kant kun je voor netwerkcommunicatie of I/O-operaties je code vereenvoudigen met async
/await
.
Door beide op de juiste manier te combineren, kun je efficiënte asynchrone verwerking bereiken.
Voorbeelden van het Gebruik van Web Worker
Voorbeeld van het uitbesteden van zware berekeningen
Hieronder volgt een voorbeeld van het uitbesteden van zware berekeningen.
1// worker.js
2onmessage = function(event) {
3 const num = event.data;
4 const result = fibonacci(num);
5 postMessage(result);
6};
7
8function fibonacci(n) {
9 if (n <= 1) return n;
10 return fibonacci(n - 1) + fibonacci(n - 2);
11}
1// Main thread
2const worker = new Worker('worker.js');
3
4worker.onmessage = function(event) {
5 console.log('Fibonacci result: ', event.data);
6};
7
8worker.postMessage(40); // Delegate heavy computation to the worker
- Deze code is een voorbeeld van het gebruik van een Web Worker om zware taken, zoals het berekenen van de Fibonaccireeks, van de hoofdthread te scheiden en uit te voeren.
Een voorbeeld van het specificeren van een taaknaam
Hieronder volgt een voorbeeld van het verzenden en ontvangen van berichten door een taaknaam te specificeren.
1// worker.js
2self.onmessage = function(event) {
3 switch (event.data.task) {
4 case 'add':
5 const result = event.data.a + event.data.b;
6 self.postMessage({ task: 'result', value: result });
7 break;
8 default:
9 self.postMessage({ task: 'error', message: 'Invalid Task' });
10 }
11};
1// Main thread
2const worker = new Worker('worker.js');
3
4worker.onmessage = function(event) {
5 switch (event.data.task) {
6 case 'result':
7 console.log('Task result: ', event.data.value);
8 break;
9 case 'error':
10 console.error('Error: ', event.data.message);
11 break;
12 }
13};
14
15worker.postMessage({ task: 'add', a: 10, b: 20 });
- Deze code is een voorbeeld van het verwerken op basis van de
task
-naam in het bericht, waarbij deWeb Worker
de berekeningsresultaten of fouten samen met de taaknaam terugstuurt naar de hoofdthread.
Notities
Houd rekening met de volgende punten bij het gebruik van Web Worker
.
- Geen toegang tot DOM
Web Worker
kan de UI niet manipuleren of de DOM benaderen. DOM-manipulaties moeten worden uitgevoerd in de hoofdthread. - Communicatie-overhead
Er is enige overhead bij het uitwisselen van gegevens tussen de hoofdthread en de
Web Worker
. Dit kan invloed hebben op de prestaties, vooral bij het frequent uitwisselen van grote hoeveelheden gegevens. - Same-origin-beleid
Web Worker
-scripts zijn onderhevig aan het same-origin-beleid. Scripts kunnen niet van verschillende domeinen worden geladen.
Het gebruik van Web Worker
kan de prestaties en responsiviteit van je applicatie verbeteren, maar het is belangrijk dit op de juiste manier te gebruiken, rekening houdend met beperkingen zoals het onvermogen om de DOM te manipuleren.
Je kunt het bovenstaande artikel volgen met Visual Studio Code op ons YouTube-kanaal. Bekijk ook het YouTube-kanaal.