本文主要是介绍详解 WebWorker 的概念、使用场景、示例,希望对大家解决编程问题提供一定的参考价值,需要的开发者们随着小编来一起学习吧!
前言
提到 WebWorker,可能有些小伙伴比较陌生,不知道是做什么的,甚至不知道使用场景,今天这篇文章就带大家一起简单了解一下什么是 webworker!
概念
WebWorker 实际上是运行在浏览器后台的一个单独的线程,因此可以执行一些耗时的操作而不会阻塞主线程。WebWorker 通过与主线程之间传递消息实现通信,这种通信是双向的。WebWorker不能直接访问 DOM,也不能使用像 window 对象这样的浏览器接口对象,但可以使用一些WebWorker 标准接口和 Navigator 对象的部分属性和方法。
为什么使用WebWorker?
- 提高应用响应能力:主线程被独占执行一些耗时的计算或操作时,会导致UI无响应。WebWorker 可以把这些任务转移到后台线程,从而保证主线程的运行,提高应用的响应能力。
- 充分利用多核CPU:现代CPU都是多核的,WebWorker 可以让 Web 应用利用多核 CPU 的并行计算能力,充分发挥计算机硬件性能。
- 避免渲染阻塞:JavaScript 运行在主线程,如果主线程一直占用,就无法执行 GUI 渲染任务,导致界面渲染受阻。WebWorker 把一些费时任务分流到后台线程就可以避免这一问题。
- 后台持续运行:WebWorker 所在后台线程可持续运行,即使页面被挂起或最小化,任务仍在后台执行,非常适合一些需要长时间运行的操作。
使用场景
一般来说,当遇到如下几种情况时可以考虑使用 WebWorker:
- 大量数据的计算/处理:比如图像处理、数据分析等
- 长时间运行的操作:如一些复杂的数学计算
- 非阻塞式操作:希望执行一些耗时操作时不阻塞主线程
示例
假设我们有一个需要计算斐波那契数列的任务,我们可以使用 Web Worker 来进行计算,以避免阻塞主线程。以下是一个简单的示例:
主线程
主线程创建 worker 实例,向子线程通过 postMessage 发送消息,通过 onmessage 监听子线程返回的数据。
const myWorker = new Worker('./worker.js')myWorker.onmessage = function (e) {console.log('Fibonacci result:', e.data)}myWorker.postMessage(40) // 请求计算斐波那契数列的第40项
worker.js
在同级目录下创建 worker.js文件,通过 onmessage 接收主线程发来的数据,计算后通过postMessage 将计算结果返回主线程。
self.onmessage = function (e) {const n = e.datalet a = 0,b = 1,tempfor (let i = 2; i <= n; i++) {temp = aa = bb = temp + b}self.postMessage(b)
}
运行结果
可以看到主线程打印出 webworker 计算的运行结果
Vue、React项目使用
接下来为大家演示 vue 以及 react 项目如何使用
Vue使用
vue版本:"vue": "^2.6.14",vue-cli版本:@vue/cli 5.0.8安装 worker-loader
页面使用
<template><div>我的页面</div></template>
<script>
export default {name: 'MyselfView',data() {return {worker: null,}},mounted() {// 创建 WebWorker 实例this.worker = new Worker(new URL('./worker.js', import.meta.url))console.log('worker: ', this.worker)this.worker.postMessage(40) // 请求计算斐波那契数列的第40项this.worker.addEventListener('message', (event) => {console.log('Fibonacci result:', event.data)})},beforeDestroy() {// 组件销毁时终止 WebWorkerthis.worker.terminate()},
}
</script>
worker.js
// worker.js
self.addEventListener('message', (e) => {console.log('e: ', e)const n = e.datalet a = 0,b = 1,tempfor (let i = 2; i <= n; i++) {temp = aa = bb = temp + b}self.postMessage(b)
})
效果
React使用
react版本: "react": "^18.2.0"
import React, { useEffect } from 'react'
// import WorkerScript from './worker.worker.js'const Demo = () => {useEffect(() => {const worker = new Worker(new URL('./worker.worker.js', import.meta.url))worker.onmessage = function (e) {console.log('Fibonacci result:', e.data)}worker.postMessage(40) // 请求计算斐波那契数列的第40项// 使用 worker ...return () => worker.terminate()}, [])return (<div><p>count的值</p></div>)
效果
注意
由于我们在项目开发时,使用不同的打包工具(vite/webpack
)。幸运的是,最新版的vite/webpack
都支持Web Worker
了。
我们可以通过:new URL()
的方式 --vite/webpack
都支持
new Worker(new URL('./worker.js', import.meta.url)
);
总结
WebWorker是一种在 Web 应用中实现多线程运行的技术,可以将耗费 CPU 的任务交给后台线程处理,避免阻塞主线程,从而提高Web应用的响应性能和用户体验。 总之,WebWorker的引入解决了Web应用长期以来在单个线程中运行所带来的诸多问题,有效提升了Web应用的运行性能和用户体验。
这篇关于详解 WebWorker 的概念、使用场景、示例的文章就介绍到这儿,希望我们推荐的文章对编程师们有所帮助!