19_HTML5 Web Workers --[HTML5 API 学习之旅]

HTML5 Web Workers 是一种允许 JavaScript 在后台线程中运行的技术,从而不会阻塞用户界面或其他脚本的执行。通过使用 Web Workers,你可以执行复杂的计算任务而不影响页面的响应速度,提升用户体验。

Web Workers 的特点

Web Workers 是 HTML5 引入的一种多线程解决方案,允许 JavaScript 代码在后台线程中运行。以下是 Web Workers 的一些关键特点:

1. 非阻塞用户界面

  • 分离任务:Web Workers 可以将耗时的任务(如复杂的计算、数据处理等)移到后台线程执行,避免阻塞主线程,从而确保用户界面的流畅性和响应性。

2. 多线程支持

  • 并发处理:通过创建多个 Worker 实例,可以同时处理不同的任务,充分利用多核处理器的能力,提高应用性能。

3. 消息传递机制

  • 通信方式:主线程和 Worker 线程之间通过 postMessage() 方法发送消息,并使用 message 事件监听器接收消息。这种机制保证了线程间的安全通信。

4. 受限的环境

  • 安全沙箱:为了防止潜在的安全问题,Worker 没有直接访问 DOM 或者某些全局对象(如 windowdocumentparent 等)的能力。然而,它们仍然可以访问一些常用的全局对象,比如 navigatorlocation

5. 生命周期管理

  • 动态控制:开发者可以根据需要创建、终止(terminate)或让 Worker 自我销毁(close)。这使得资源管理更加灵活,可以根据实际情况优化性能。

6. 独立于页面生命周期

  • 持续运行:尽管 Web Workers 依赖于创建它的页面,但一旦启动,它们可以在页面刷新或导航到其他页面时继续运行,直到被显式终止或页面关闭为止。

7. 同源限制

  • 安全性考虑:出于安全原因,Web Workers 只能加载来自同一来源(协议、域名、端口都相同)的脚本文件。跨域请求需要特别处理,通常涉及 CORS(跨域资源共享)策略。

8. 有限的数据共享

  • 隔离性:每个 Worker 都有自己的作用域和内存空间,不能直接与其他 Worker 或主线程共享变量或状态。所有数据交换必须通过消息传递来完成。

9. 调试支持

  • 开发工具集成:现代浏览器提供了对 Web Workers 的良好支持,包括专用的调试面板和日志输出功能,方便开发者进行故障排除和性能分析。

10. 多种类型

  • Dedicated Workers:专门为单个脚本服务,只能与创建它的脚本通信。
  • Shared Workers:允许多个浏览上下文(例如不同标签页)共享同一个 Worker 实例,实现更广泛的任务协作。
  • Service Workers:用于实现高级功能,如推送通知、后台同步以及离线缓存等,它可以在用户关闭浏览器后仍然保持活跃。

这些特点共同构成了 Web Workers 的强大功能集,使其成为构建高性能、响应式的Web应用程序的重要组成部分。特别是对于那些需要执行复杂计算或处理大量数据的应用来说,Web Workers 提供了一种有效的方式来提升用户体验。

创建和使用 Web Worker

以下是四个创建和使用 Web Worker 的示例,涵盖了不同类型的任务和应用场景。每个示例都展示了如何创建 Worker、发送消息以及处理来自 Worker 的响应。

示例 1:基本的 Web Worker

场景:在后台计算大数目的平方根,并将结果返回给主线程。

worker.js (Worker 文件)
self.onmessage = function(event) {let data = event.data;console.log('Received:', data);// 计算平方根let result = Math.sqrt(data);// 发送结果回主线程self.postMessage(result);
};
主页面代码
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Basic Web Worker</title>
<script>
if (window.Worker) {var myWorker = new Worker('worker.js');myWorker.postMessage(1600); // 发送数据到 WorkermyWorker.onmessage = function(event) {console.log('Square root:', event.data);};
} else {console.log('Your browser does not support Web Workers.');
}
</script>
</head>
<body>
</body>
</html>

在这里插入图片描述

示例 2:Shared Worker

场景:多个标签页共享同一个 Worker 来同步计数器值。

shared-worker.js (Shared Worker 文件)
var clients = [];self.onconnect = function(e) {var port = e.ports[0];clients.push(port);port.onmessage = function(event) {let action = event.data;if (action === 'increment') {for (let client of clients) {client.postMessage('Counter incremented');}}};port.start();
};
主页面代码(适用于多个标签页)
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Shared Worker Example</title>
<script>
if (window.SharedWorker) {var sharedWorker = new SharedWorker('shared-worker.js');sharedWorker.port.onmessage = function(event) {console.log(event.data);};// sharedWorker.port.postMessage('increment');setTimeout(function() {document.querySelector('button').onclick = function() {sharedWorker.port.postMessage('increment');};}, 300); // 1000 毫秒 = 1 秒} else {console.log('Your browser does not support Shared Workers.');
}
</script>
</head>
<body>
<button>Increase Counter</button>
</body>
</html>

在这里插入图片描述

示例 3:处理大量数据

场景:排序一个非常大的数组而不阻塞UI线程。

sort-worker.js (Worker 文件)
/*** 当Worker接收到消息时,此事件处理函数会被触发* 它对接收到的数据进行排序,并将排序后的结果发回* * @param {MessageEvent} event - 事件对象,包含从主线程发送过来的数据*/
self.onmessage = function(event) {// 从事件对象中获取传递过来的数组let array = event.data;// 对数组进行排序,确保数组中的数字按升序排列array.sort((a, b) => a - b);// 将排序后的数组发回主线程self.postMessage(array);
};
主页面代码
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Heavy Data Processing</title>
<script>
// 检查浏览器是否支持Web Workers
if (window.Worker) {// 创建一个新的Web Worker对象var sortWorker = new Worker('sort-worker.js');// 生成一个包含100万个随机整数的数组let largeArray = Array.from({length: 1e6}, () => Math.floor(Math.random() * 1e6));// 将大数组发送给Web Worker进行排序sortWorker.postMessage(largeArray);// 接收Web Worker返回的排序后的数组sortWorker.onmessage = function(event) {// 打印排序后的数组的前10个元素console.log('Sorted array:', event.data.slice(0, 10));};
} else {// 如果浏览器不支持Web Workers,打印提示信息console.log('Your browser does not support Web Workers.');
}
</script>
</head>
<body>
</body>
</html>

在这里插入图片描述

示例 4:定时任务

场景:每隔一段时间向主线程发送更新通知。

timer-worker.js (Worker 文件)
// 每秒发送当前时间的时分秒表示,作为时间服务工作者的主循环
setInterval(function() {// 创建一个日期对象,并使用toLocaleTimeString方法获取当前时间的时分秒表示// self.postMessage用于向工作者的监听者发送消息,在这里发送的是当前时间self.postMessage(new Date().toLocaleTimeString());
}, 1000);
主页面代码
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>Timer Worker</title>
<script>
// 检查浏览器是否支持Web Workers
if (window.Worker) {// 创建一个新的Web Worker对象,加载'timer-worker.js'文件var timerWorker = new Worker('timer-worker.js');// 定义接收到Web Worker消息时的处理函数// 当Web Worker发送消息时,此函数将被调用,输出接收到的时间更新信息timerWorker.onmessage = function(event) {console.log('Time update:', event.data);};
} else {// 如果浏览器不支持Web Workers,输出提示信息console.log('Your browser does not support Web Workers.');
}
</script>
</head>
<body>
</body>
</html>

在这里插入图片描述

这些示例展示了不同类型的 Web Worker 如何被用来解决各种问题,从简单的计算任务到复杂的交互式应用。根据你的具体需求和技术栈选择最适合的 Worker 类型。

注意事项

使用 HTML5 Web Workers 时,有几个重要的注意事项和最佳实践可以帮助你更有效地利用这项技术,并避免常见的陷阱。以下是详细的注意事项列表:

1. 浏览器兼容性

  • 检查支持情况:尽管大多数现代浏览器都支持 Web Workers,但在使用之前应该检查目标用户的浏览器是否支持。可以通过 if (window.Worker) 这样的条件来检测支持。

2. 同源策略

  • 资源加载限制:Web Workers 只能加载来自相同来源(协议、域名、端口)的脚本文件。如果你需要从不同来源加载脚本,则需要确保服务器正确配置了 CORS(跨域资源共享)头。

3. 通信机制

  • 消息传递:Worker 和主线程之间的通信是通过 postMessage() 方法发送消息以及监听 message 事件实现的。所有传递的数据都是通过结构化克隆算法复制的,因此不适合传递大量数据或复杂对象。

4. 性能开销

  • 创建和销毁成本:创建和销毁 Worker 都有一定的性能开销。对于轻量级任务,可能不值得启动一个新的 Worker;而对于复杂计算,使用 Worker 则非常有用。考虑将多个小任务合并为一个较大的任务来处理,以减少频繁创建和销毁 Worker 的次数。

5. 内存管理

  • 及时终止:当不再需要 Worker 时,应该调用其 terminate() 方法来停止它,释放占用的资源。长期运行且不再使用的 Worker 会浪费系统资源。
  • 避免内存泄漏:确保没有未处理的消息队列或者定时器在 Worker 中持续运行,这可能导致内存泄漏。

6. 安全性

  • 受限环境:Workers 没有直接访问 DOM 或者某些全局对象的能力,这是为了提高安全性。不要试图绕过这些限制,因为它们有助于保护用户隐私和应用程序的安全性。

7. 调试困难

  • 开发工具支持:虽然现代浏览器提供了对 Web Workers 的调试支持,但与普通 JavaScript 脚本相比,调试 Worker 仍然较为复杂。尽量编写清晰易懂的代码,并充分利用日志记录和断点调试功能。

8. 错误处理

  • 捕获异常:在 Worker 内部发生的错误不会自动传播到主线程,因此你需要显式地添加错误处理逻辑。可以监听 Worker 的 error 事件来捕获并处理错误。

9. 数据共享

  • 独立作用域:每个 Worker 都有自己的作用域和内存空间,不能直接与其他 Worker 或主线程共享变量或状态。所有数据交换必须通过消息传递完成。

10. 文件路径

  • 相对路径问题:如果 Worker 文件使用相对路径加载,那么它的路径是相对于主页面的位置,而不是相对于 Worker 文件本身。确保路径设置正确,特别是在复杂的项目结构中。

11. 类型选择

  • 选择合适的 Worker 类型:根据需求选择 Dedicated Worker 或 Shared Worker。Dedicated Worker 是专门为单个脚本服务的,而 Shared Worker 可以被多个浏览上下文共享。

12. Service Workers

  • 区分用途:不要混淆 Web Workers 和 Service Workers。Service Workers 主要用于实现推送通知、后台同步以及离线缓存等功能,它们的工作方式与 Web Workers 不同。

遵循以上注意事项,可以帮助你在使用 Web Workers 时更加高效和安全,同时确保你的应用能够提供良好的用户体验。

类型

HTML5 Web Workers 提供了多种类型的 Worker,每种类型都有其特定的用途和适用场景。以下是主要的 Web Worker 类型及其特点:

1. Dedicated Workers

  • 定义:Dedicated Workers 是最常见的 Worker 类型,它们专门为创建它们的脚本或页面服务。
  • 通信:仅与创建它的脚本或页面进行通信,不能与其他 Worker 或其他浏览上下文共享。
  • 生命周期:由创建它的脚本控制,当不再需要时可以显式终止(terminate())或让 Worker 自我销毁(close())。
  • 使用场景:适合用于执行单个任务或与单个页面相关的后台处理。
创建 Dedicated Worker 示例:
// 在主页面中
var worker = new Worker('worker.js');worker.postMessage('Start processing');
worker.onmessage = function(event) {console.log('Message from worker:', event.data);
};

2. Shared Workers

  • 定义:Shared Workers 可以被多个浏览上下文(如不同的标签页、iframe 等)共享。
  • 通信:通过 Port 对象与各个客户端通信,每个客户端都需要调用 port.start() 来开始消息交换。
  • 生命周期:只要有一个客户端连接着 Shared Worker,它就会继续运行;当所有客户端断开连接后,Worker 才会关闭。
  • 使用场景:适用于需要在多个浏览器窗口或标签页之间共享数据或状态的应用程序。
创建 Shared Worker 示例:
// 在主页面中
var sharedWorker = new SharedWorker('shared-worker.js');sharedWorker.port.start();
sharedWorker.port.postMessage('Hello from page');
sharedWorker.port.onmessage = function(event) {console.log('Message from shared worker:', event.data);
};

3. Service Workers

  • 定义:Service Workers 是一种特殊的 Worker,主要用于实现离线支持、推送通知和后台同步等功能。
  • 通信:可以在用户关闭浏览器后仍然保持活跃,并拦截和处理网络请求。
  • 生命周期:Service Worker 的生命周期是由浏览器管理的,它可以被激活、等待安装或直接跳过等待阶段。
  • 使用场景:非常适合用于构建 PWA(渐进式Web应用),提供更好的用户体验,如离线访问、快速加载和推送通知等。
注册 Service Worker 示例:
if ('serviceWorker' in navigator) {window.addEventListener('load', function() {navigator.serviceWorker.register('/service-worker.js').then(function(registration) {console.log('ServiceWorker registration successful with scope: ', registration.scope);}, function(err) {console.log('ServiceWorker registration failed: ', err);});});
}

总结

  • Dedicated Workers:适用于需要在后台执行特定任务但不需要跨多个浏览上下文共享的情况。
  • Shared Workers:当你有多个浏览上下文需要共享同一个 Worker 实例时非常有用。
  • Service Workers:为Web应用提供了更强大的功能,如离线支持和推送通知,是构建现代Web应用不可或缺的一部分。

选择合适的 Worker 类型取决于你的具体需求和技术目标。正确地选择和使用 Worker 类型可以显著提升Web应用的性能和用户体验。

本文来自互联网用户投稿,该文观点仅代表作者本人,不代表本站立场。本站仅提供信息存储空间服务,不拥有所有权,不承担相关法律责任。如若转载,请注明出处:http://www.rhkb.cn/news/496021.html

如若内容造成侵权/违法违规/事实不符,请联系长河编程网进行投诉反馈email:809451989@qq.com,一经查实,立即删除!

相关文章

数据分析篇001

目录 一、数据是什么&#xff1f; 二、数据能做什么&#xff1f; 三、数据应用四步骤 第一步---搭建数据体系 第二步---积累数据资产 第三步---完成数据分析 第四步---实现数据应用 四、数据的三种性质 变异性 规律性&#xff08;以正态分布为例&#xff09; 客观性…

Java线程池面试题

为什么要用线程池 降低资源消耗&#xff1a;通过重复利用已创建的线程降低线程创建和销毁造成的消耗提高响应速度&#xff1a;当任务到达时&#xff0c;任务可以不需要等到线程创建就能立即执行方便管理线程&#xff1a;线程是稀缺资源&#xff0c;如果无条件地创建&#xff0…

校史馆云展厅适合远程教学吗?

随着信息技术的飞速发展&#xff0c;远程教学已经成为教育领域的一个重要趋势。 校史馆作为学校文化传承的重要场所&#xff0c;承载着丰富的历史信息和教育资源。 那么&#xff0c;将校史馆搬到云端&#xff0c;构建云展厅&#xff0c;是否适合远程教学呢&#xff1f; 下面…

【安全编码】Web平台如何设计防止重放攻击

我们先来做一道关于防重放的题&#xff0c;答案在文末 防止重放攻击最有效的方法是&#xff08; &#xff09;。 A.对用户密码进行加密存储使用 B.使用一次一密的加密方式 C.强制用户经常修改用户密码 D.强制用户设置复杂度高的密码 如果这道题目自己拿不准&#xff0c;或者…

GJB289A总线典型网络理论分析

1.GJB289A总线典型网络理论分析 根据相关标准&#xff0c;“某个支路的故障不影响整个系统”及耦合变压器特性&#xff0c;本文在仿真与实测时均采用典型的一发一收两端口总线网络。 典型两端口总线网络电气结构如图1所示&#xff0c;包含终端匹配电阻、故障隔离电阻、耦合变…

基于SpringBoot的4S店汽车销售管理系统的设计与实现

一、课题背景 为汽车销售公司设计了一个汽车管理系统 技术&#xff1a;前台采用网页技术&#xff0c;后端采用SpringBoottMybatistvue 项目 描述&#xff1a;随着人们生活水平的不断提高&#xff0c;人们对汽车的消费和需求也越来越旺盛。多汽车销售公司仍然采用人工记账的传…

SQL子查询和having实例

有2个表如下&#xff1b;一个是站点信息&#xff0c;一个是站点不同时间的访问量&#xff0c; 现在要获取总访问量大于200的网站&#xff1b; 先执行如下sql&#xff0c;不包括having子句看一下&#xff0c;获得的是所有站点的总访问量&#xff1b; 这应是一个子查询&#xf…

SpringAI人工智能开发框架006---SpringAI多模态接口_编程测试springai多模态接口支持

可以看到springai对多模态的支持. 同样去创建一个项目 也是跟之前的项目一样,修改版本1.0.0 这里 然后修改仓库地址,为springai的地址 然后开始写代码

【UE5 C++课程系列笔记】13——GameInstanceSubsystem的简单使用

目录 概念 基本使用案例 效果 步骤 概念 UGameInstanceSubsystem 类继承自 USubsystem&#xff0c;它与 GameInstance 紧密关联&#xff0c;旨在为游戏提供一种模块化、可方便扩展和管理的功能单元机制。在整个游戏运行期间&#xff0c;一个 GameInstance 可以包含多个 UGa…

mac_录屏

参考&#xff1a; mac m1上系统内录方法BlackHole代替soundflower录音(附安装包) https://blog.csdn.net/boildoctor/article/details/122765119录屏后没声音&#xff1f;这应该是 Mac&#xff08;苹果电脑&#xff09; 内录声音最优雅的解决方案了 https://www.bilibili.com/…

CTF MISC 简单的脚本的撰写 -- 进制转换篇

前言 为什么学习 脚本 &#xff1f; 当脚本小子的基础也是需要看懂代码的好吧 虽然很多工具都可以解码 进制转换 ascii 但是 前 128位的ascii 可以转 那后 128位呢 一般工具是不识别的所以脚本还需自己学 【ASCII】完整ascii码表0-127 扩展表128-255-CSDN博客 前言知识…

我的Opencv

1.安装Opencv pip install opencv-python 2.读取图像 3.写图像 4. 显示图像 5.waitKey() 6.读视频并播放视频 7.写视频 8. 获取摄像头视频 9.色彩转换 # BGR to GRAY imgGRAY cv2.cvtColor(img, cv2.COLOR_BGR2GRAY) # BGR to RGB imgRGB cv2.cvtColor(img, cv2.COLOR_…

Go语言及MongoDB数据库安装配置详解!

Go语言安装 首先讲一下go语言的安装&#xff0c;这部分可直接从官网下载&#xff0c;基本上一键配置的&#xff1a; 官网地址&#xff1a;All releases - The Go Programming Language 选择自己对应系统的安装包&#xff0c;这里官网提供了5种不同的包可自行下载 之后便是默认…

Redis - Token JWT 概念解析及双token实现分布式session存储实战

Token 定义&#xff1a;令牌&#xff0c;访问资源接口&#xff08;API&#xff09;时所需要的资源凭证 一、Access Token 定义&#xff1a;访问资源接口&#xff08;API&#xff09;时所需要的资源凭证&#xff0c;存储在客户端 组成 组成部分说明uid用户唯一的身份标识time…

sentinel限流+其他

quick-start | Sentinel sentinel 作用 限流 熔断降级 1&#xff0c;限制什么 QPS 并发线程数 2&#xff0c;限制什么 资源&#xff0c;什么资源 服务&#xff0c;方法&#xff0c;接口&#xff0c;或者一段代码 3&#xff0c;实现方式 配置规则 注解 其他 Java常见5种限流…

JVM实战—2.JVM内存设置与对象分配流转

大纲 1.JVM内存划分的原理细节 2.对象在JVM内存中如何分配如何流转 3.部署线上系统时如何设置JVM内存大小 4.如何设置JVM堆内存大小 5.如何设置JVM栈内存与永久代大小 6.问题汇总 1.JVM内存划分的原理细节 (1)背景引入 (2)大部分对象的存活周期都是极短的 (3)少数对象…

Eclipse常用快捷键详解

文章目录 Eclipse常用快捷键详解一、引言二、编辑快捷键三、选择和移动快捷键四、行操作快捷键五、搜索和导航快捷键六、调试快捷键七、重构快捷键八、其他快捷键九、使用案例场景一&#xff1a;代码编写代码示例 场景二&#xff1a;代码调试场景三&#xff1a;代码重构代码示例…

oscp学习之路,Kioptix Level2靶场通关教程

oscp学习之路&#xff0c;Kioptix Level2靶场通关教程 靶场下载&#xff1a;Kioptrix Level 2.zip 链接: https://pan.baidu.com/s/1gxVRhrzLW1oI_MhcfWPn0w?pwd1111 提取码: 1111 搭建好靶场之后输入ip a看一下攻击机的IP。 确定好本机IP后&#xff0c;使用nmap扫描网段&…

linux系统上SQLPLUS的重“大”发现

SQL plus版本&#xff1a; [oraclepg-xc2 ~]$ sqlplus -v SQL*Plus: Release 19.0.0.0.0 - Production Version 19.3.0.0.0 操作系统&#xff1a;CentOS Linux 7 (Core) 数据库&#xff1a;Oracle 19c Version 19.3.0.0.0 同样的SQL脚本在windos CMD sqlplus 执行没问题。…

Qt使用QZipWriter和QZipReader来解压、压缩文件

首先感谢这位博主的无私奉献&#xff1a;Qt - 实现压缩文件、文件夹和解压缩操作 - [BORUTO] - 博客园 多文件和目录压缩时&#xff0c;不改变原始文件和目录的相对位置结构&#xff0c;需要在addFile和addDirectory时&#xff0c;需要带上相对路径&#xff0c;如下&#xff1…