什么是Web Worker?如何使用Web Worker?

server/2024/11/29 21:19:07/

1. 什么是 Web Worker?

JavaScript 语言采用的是单线程的,也就是说,所有任务只能在一个线程上完成,一次只能做一件事。前面的任务没做完,后面的任务只能等着。

Web Worker 是一种在浏览器中实现多线程处理的技术,允许在后台线程中执行脚本,从而避免长时间运行的脚本阻塞用户界面。

Web Worker 的作用,就是为 JavaScript 创造多线程环境,允许主线程创建 Worker 线程,将一些任务分配给后者运行。在主线程运行的同时,Worker 线程在后台运行,两者互不干扰。等到 Worker 线程完成计算任务,再把结果返回给主线程。

主线程与 Worker 之间的通信内容,可以是文本,也可以是对象。

2. Web Worke主要特点

  1. 同源限制: Worker 线程必须与主线程的脚本文件同源。

  2. 通信机制:主线程和 Worker 线程之间不能直接通信,必须通过消息传递(postMessageonmessage)进行通信。消息传递是异步的,确保了线程间的隔离和安全性。

    双方都使用 postMessage() 方法发送各自的消息,使用 onmessage 事件处理函数来响应消息(消息被包含在 message 事件的 data 属性中)。这个过程中数据并不是被共享而是被复制。

    😊为什么消息传递中的数据不是被共享而是被复制?
    ● 与共享内存不同,两个线程之间并没有直接访问对方内存的能力。每个线程只能访问自己的内存空间,通过消息传递的方式进行通信。
    ● 复制数据可以避免多个线程同时修改同一块内存,从而避免数据竞争和线程安全问题。

  3. 资源限制: Worker 线程不能访问 DOM,也不能使用某些全局对象(如 window),也无法读取本地文件,即不能打开本机的文件系统(file://),它所加载的脚本,必须来自网络。

3. Web Worker的基本用法

3.1 主线程

主线程采用new命令,调用Worker()构造函数,新建一个 Worker 线程。

javascript">const worker = new Worker('work.js');

Worker()构造函数的参数是一个来自网络的脚本文件,该文件就是 Worker 线程所要执行的任务。由如果下载没有成功(比如404错误),Worker 就会默默地失败。
然后,主线程调用·worker.postMessage() 方法,向 Worker 发消息。

<!DOCTYPE html>
<html lang="en">
<head><meta charset="UTF-8"><meta name="viewport" content="width=device-width, initial-scale=1.0"><title>Web Worker Example</title>
</head>
<body><button id="start">Start Calculation</button><p id="result"></p><script>javascript">// 主线程采用new命令,调用Worker()构造函数,创建一个新的 Workerconst worker = new Worker('worker.js');document.getElementById('start').addEventListener('click', function() {// 向 Worker 发送数据const data = 10;worker.postMessage(data);});// 监听 Worker 发送的消息worker.onmessage = function(e) {//事件对象的data属性可以获取 Worker 发来的数据const result = e.data;document.getElementById('result').textContent = 'Result: ' + result;};// 监听 Worker 的错误worker.onerror = function(error) {console.error('Worker error:', error);};</script>
</body>
</html>

Worker 完成任务以后,主线程就可以把它关掉。

javascript">worker.terminate();

3.2 Worker 线程

Worker 线程内部需要有一个监听函数,监听message事件。

javascript">// worker.js
self.onmessage = function(e) {const data = e.data;console.log('Received data:', data);// 处理数据const result = data * 2;// 发送结果回主线程self.postMessage(result);
};

上面代码中,self代表子线程自身,即子线程的全局对象。也等同于下面写法:

javascript">self.addEventListener('message', function (e) {const data = e.data;console.log('Received data:', data);// 处理数据const result = data * 2;// 发送结果回主线程self.postMessage(result);
}, false);

关闭Worker 线程:

javascript">self.close();

Worker 加载脚本:

javascript">importScripts('script1.js');
// 同时加载多个脚本
importScripts('script1.js', 'script2.js');

4.Web Worker的API

主线程:
worker.onerror:指定 error 事件的监听函数。
worker.onmessage:指定 message 事件的监听函数,发送过来的数据在Event.data属性中。
worker.onmessageerror:指定 messageerror 事件的监听函数。发送的数据无法序列化成字符串时,会触发这个事件。
worker.postMessage():向 Worker 线程发送消息
worker.terminate():立即终止 Worker 线程。

Worker 线程:
self.name: Worker 的名字。该属性只读,由构造函数指定。
self.onmessage:指定message事件的监听函数。
self.onmessageerror:指定 messageerror 事件的监听函数。发送的数据无法序列化成字符串时,会触发这个事件。
self.close():关闭 Worker 线程。
self.postMessage():向产生这个 Worker 线程发送消息。
self.importScripts():加载 JS 脚本。


http://www.ppmy.cn/server/145994.html

相关文章

详谈面试题:Vue、React为什么使用虚拟DOM

虚拟DOM是一种在前端框架中广泛使用的技术&#xff0c;它可以提升开发效率。那么国外流行的框架svelte没有使用虚拟DOM&#xff0c;而是直接操作真实DOM&#xff0c;效率依然很高。为什么Vue和React不采用这种方式呢&#xff1f; 目录 一、框架设计 二、解耦运行环境 三、总…

GPU 选型指南

根据 GPU 架构的不同&#xff0c;可分为以下几类&#xff1a; NVIDIA Volta 架构 代表型号&#xff1a; V100 配备第二代 Tensor Core&#xff0c;是较早支持深度学习的 GPU&#xff0c;仍适用于部分训练任务。性能特点&#xff1a;相比后续架构&#xff0c;V100 的训练性能…

【es6】原生js在页面上画矩形添加选中状态高亮及显示调整大小控制框(三)

接上篇文章&#xff0c;这篇实现下选中当前元素显示调整大小的控制框&#xff0c;点击document取消元素的选中高亮状态效果。 实现效果 代码逻辑 动态生成控制按钮矩形,并设置响应的css // 动态添加一个调整位置的按钮addScaleBtn(target) {const w target.offsetWidth;con…

Flutter:encrypt插件 AES加密处理

1、pubspec.yaml导入插件 cupertino_icons: ^1.0.8 # 密码加密 encrypt: 5.0.3encrypt封装 import package:encrypt/encrypt.dart; /// 加密类 class EncryptUtil {static final EncryptUtil _instance EncryptUtil._internal();factory EncryptUtil() > _instance;Encrypt…

C#身份证识别接口集成、身份证文字信息提取、身份证信息录入

身份证识别接口为什么会受到互联网平台的青睐&#xff1f;传统的身份验证方式往往需要用户手动输入个人信息&#xff0c;这不仅耗时耗力&#xff0c;还容易出现误操作影响身份认证结果的现象。翔云身份证识别接口通过先进的OCR&#xff08;光学字符识别&#xff09;技术&#x…

使用 Python 的 pdfplumber 库高效解析 PDF 文件

使用 Python 的 pdfplumber 库高效解析 PDF 文件 PDF 文件是日常办公和数据处理中常见的文件格式&#xff0c;而 pdfplumber 是一个专为 PDF 文件解析设计的 Python 库&#xff0c;可以轻松提取文本、表格、图像等内容。本文将介绍 pdfplumber 的基本功能、使用方法&#xff0…

Rust如何编制前端路由

目的&#xff1a;根据前端build文件夹下的目录结构&#xff0c;生成路由&#xff0c;将前端html文件返回。 /// 设置 HTML 文件路由 pub fn route(cfg: &mut web::ServiceConfig) {if Path::new("client/build/index.html").exists() {let index_content match…

阅读《基于蒙特卡洛法的破片打击无人机易损性分析》_笔记

目录 基本信息 1 引言 1.1 主要研究内容 1.2 研究必要性&#xff08;为什么要研究&#xff09; 1.3 该领域研究现状&#xff08;别人做了什么/怎么做的&#xff09; 2 主要研究过程&#xff08;我们做了什么&#xff09; 2.1 建立目标仿真模型 2.2 确定毁伤依据 2.3 无…