HTML5 – Web Workers

HTML5 – Web Workers

JavaScript被设计成在单线程环境中运行,意味着多个脚本无法同时运行。考虑一种情况,您需要处理UI事件、查询和处理大量API数据以及操作DOM。

当CPU利用率高的情况下,JavaScript会使您的浏览器挂起。让我们以一个简单的例子来说明JavaScript的问题,JavaScript通过一个大循环的情况:

<!DOCTYPE HTML>

<html>
   <head>
      <title>大循环</title>

      <script>
         function bigLoop() {

            for (var i = 0; i <= 10000; i += 1) {
               var j = i;
            }
            alert("已完成 " + j + " 次迭代");
         }

         function sayHello(){
            alert("您好先生....");
         }
      </script>

   </head>

   <body>
      <input type = "button" onclick = "bigLoop();" value = "Big Loop" />
      <input type = "button" onclick = "sayHello();" value = "Say Hello" />
   </body>
</html>

它将产生以下结果 –

HTML5 - Web Workers

当您点击“Big Loop”按钮时,在Firefox中显示以下结果 –

HTML5 - Web Workers

什么是Web Workers?

上述情况可以使用 Web Workers 进行处理,Web Workers将执行所有计算密集型任务,而不会中断用户界面并通常在单独的线程上运行。

Web Workers允许长时间运行的脚本,这些脚本不会被响应点击或其他用户交互的脚本中断,并允许执行长时间任务而无需放弃以保持页面响应。

Web Workers是后台脚本,它们相对较重,不适合大量使用。例如,在每个四兆像素图像的每个像素中启动一个工作线程是不合适的。

当脚本在Web Worker中执行时,它不能访问Web页面的window对象(window.document),这意味着Web Workers没有直接访问Web页面和DOM API的权限。虽然Web Workers无法阻止浏览器UI,但它们仍然可以消耗CPU周期并使系统反应不够灵敏。

Web Workers如何工作?

Web Workers使用JavaScript文件的URL初始化,该文件包含工作线程将执行的代码。这段代码设置事件侦听器并与从主页面生成的脚本通信。下面是简单的语法:

var worker = new Worker('bigLoop.js');

如果指定的JavaScript文件存在,则浏览器将生成一个新的工作线程,该线程将异步下载。如果您的路径返回404错误,则工作线程将默默地失败。

如果您的应用程序具有多个支持JavaScript文件,则可以使用 importScripts() 方法将它们导入,该方法以文件名(由逗号分隔的参数)作为参数,如下所示:

importScripts("helper.js", "anotherHelper.js");

一旦Web Worker被启动,Web Worker与其父页面之间的通信使用 postMessage() 方法进行。根据您的浏览器/版本,postMessage()可以将字符串或JSON对象作为其单个参数接受。

Web Worker传递的消息使用主页面中的 onmessage 事件来访问。现在让我们使用Web Worker编写我们的bigLoop示例。以下是主页面(hello.htm),它将生成一个Web Worker来执行循环并返回变量 j 的最终值:

<!DOCTYPE HTML>

<html>
   <head>
      <title>大循环</title>

      <script>
         var worker = new Worker('bigLoop.js');

         worker.onmessage = function (event) {
            alert("已完成" + event.data + "次迭代");
         };

         function sayHello() {
            alert("您好....");
         }
      </script>
   </head>

   <body>
      <input type = "button" onclick = "sayHello();" value = "打招呼"/>
   </body>
</html>

下面是bigLoop.js文件的内容。此文件使用 postMessage() API将通信传回主页−

for (var i = 0; i <= 1000000000; i += 1) {
   var j = i;
}
postMessage(j);

这将产生以下结果 −

HTML5 - Web Workers

停止 Web Workers

Web Workers自己无法停止,但启动它们的页面可以通过调用 terminate() 方法来停止它们。

worker.terminate();

终止的Web Worker将不再响应消息或执行任何其他计算。您无法重新启动工作者;相反,您可以使用相同的URL创建新的工作者。

错误处理

以下显示了在Web Worker JavaScript文件中记录错误到控制台的错误处理函数示例。通过错误处理代码,上面的示例将变为以下样式−

<!DOCTYPE HTML>

<html>
   <head>
      <title>大循环</title>

      <script>
         var worker = new Worker('bigLoop.js');

         worker.onmessage = function (event) {
            alert("已完成" + event.data + "次迭代");
         };

         worker.onerror = function (event) {
            console.log(event.message, event);
         };

         function sayHello() {
            alert("您好....");
         }
      </script>
   </head>

   <body>
      <input type = "button" onclick = "sayHello();" value = "打招呼"/>
   </body>
</html>

检查浏览器支持

以下是检测浏览器中Web Worker功能是否受支持的语法−

<!DOCTYPE HTML>

<html>
   <head>
      <title>大循环</title>
      <script src = "/js/modernizr-1.5.min.js"></script>

      <script>
      function myFunction() {

         if (Modernizr.webworkers) {
            alert("恭喜您!!您有Web Workers支持。");
         } else {
            alert("对不起!!您没有Web Workers支持。");
         }
      }
      </script>
   </head>

   <body>
      <button onclick = "myFunction()">点我</button>
   </body>
</html>

这将产生以下结果 −

HTML5 - Web Workers

Python教程

Java教程

Web教程

数据库教程

图形图像教程

大数据教程

开发工具教程

计算机教程