HTML5之Javascript多线程的详解


本文摘自PHP中文网,作者黄舟,侵删。

Javascript执行机制
在HTML5之前,浏览器中JavaScript的运行都是以单线程的方式工作的,虽然有多种方式实现了对多线程的模拟(例如:Javascript 中的 setinterval 方法,setTimeout 方法等),但是在本质上程序的运行仍然是由 JavaScript 引擎以单线程调度的方式进行的。在 HTML5 中引入的工作线程使得浏览器端的 Javascript 引擎可以并发地执行 Javascript 代码,从而实现了对浏览器端多线程编程的良好支持。

Javascript中的多线程 - WebWorker
HTML5 中的 Web Worker 可以分为两种不同线程类型,一个是专用线程 Dedicated Worker,一个是共享线程 Shared Worker。两种类型的线程各有不同的用途。

专用型web worker

  专用型worker与创建它的脚本连接在一起,它可以与其他的worker或是浏览器组件通信,但是他不能与DOM通信。专用的含义,就是这个线程一次只处理一个需求。专用线程在除了IE外的各种主流浏览器中都实现了,可以放心使用。
创建线程
创建worker很简单,只要把需要在线程中执行的JavaScript文件的文件名传给构造函数就可以了。

线程通信
在主线程与子线程间进行通信,使用的是线程对象的postMessage和onmessage方法。不管是谁向谁发数据,发送发使用的都是postMessage方法,接收方都是使用onmessage方法接收数据。postMessage只有一个参数,那就是传递的数据,onmessage也只有一个参数,假设为event,则通过event.data获取收到的数据。

发送JSON数据
JSON是JS原生支持的东西,不用白不用,复杂的数据就用JSON传送吧。例如:

1

postMessage({'cmd': 'init', 'timestamp': Date.now()});

处理错误
当线程发生错误的时候,它的onerror事件回调会被调用。所以处理错误的方式很简单,就是挂接线程实例的onerror事件。这个回调函数有一个参数error,这个参数有3个字段:message - 错误消息;filename - 发生错误的脚本文件;lineno - 发生错误的行。

销毁线程
在线程内部,使用close方法线程自己销毁自己。在线程外部的主线程中,使用线程实例的terminate方法销毁线程。

HTML代码:

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

<script type="text/javascript">

   

onload

 = function(){

      var worker =

new

 Worker('fibonacci.js'); 

      worker.onmessage = function(event) {

        console.log("Result:" + event.data);

      };

      worker.onerror = function(error) {

        console.log("Error:" + error.message);

      };

      worker.postMessage(40);

  

  </script>

脚本文件fibonacci.js代码:

1

2

3

4

5

6

7

8

9

10

11

12

//fibonacci.js

var fibonacci = function(n) {

     

return

 n < 2 ? n : arguments.c

all

ee(n - 1) + arguments.callee(n - 2);

};

onmessage = function(event) {

    var n = parseInt(event.data, 10);

    postMessage(fibonacci(n));

};

把它们放到相同的目录,运行页面文件,查看控制台,可以看到运行的结果。
这里还有一点,在主线程中,onmessage事件可以使用另外一种方式挂接:

1

2

3

4

5

worker.addEvent

List

ener('message', function(event) {

   console.log("Result:" + event.data);

}, false);

个人觉得很麻烦,不如用onmessage直接。

使用其他脚本文件
工作线程可以使用全局方法importScripts来加载和使用其他的域内脚本文件或者类库。例如下面都是合法的使用方式:

1

2

3

importScripts();                       

importScripts('foo.js');               

importScripts('foo.js', 'bar.js');

导入以后,可以直接使用这些文件中的方法。看一个网上的小例子:

1

2

3

4

5

6

7

8

9

10

11

12

13

14

15

16

17

mportScripts('math_utilities.js');

  

 onmessage = function (event)

 {

   var first = event.data.first;

   var second = event.data.second;

   calculate(first,second);

 };

  

 function calculate(first,second) {

    //do the calculation work

   var common_divisor=divisor(first,second);

   var common_multiple=multiple(first,second);

   postMessage("Work done! " +

      "The least common multiple is " + common_divisor  +

      " and the greatest common divisor is "+common_multiple);

 }

网上也有网友想到了利用这里的importScripts方法解决资源预加载的问题(浏览器预先加载资源,而不会对资源进行解析和执行),道理也很简单。

阅读剩余部分

相关阅读 >>

javascript如何让图片自动变换

聊聊javascript人脸识别技术

javascript 从定义到执行,需要知道的事

移动端h5中百度地图的click事件的介绍(代码示例)

javascript如何执行上下文

关于HTML5中图片抛物线运动技巧分享

js如何判断值是否数字

javascript实现utf-8编解码

h5页面如何调用摄像头代码分享

javascript xml怎么转json

更多相关阅读请进入《HTML5》频道 >>




打赏

取消

感谢您的支持,我会继续努力的!

扫码支持
扫码打赏,您说多少就多少

打开支付宝扫一扫,即可进行扫码打赏哦

分享从这里开始,精彩与您同在

评论

管理员已关闭评论功能...