webWoker

    它允许开发人员编写能够长时间运行而不被用户所中断的后台程序,
    去执行事务或者逻辑,并同时保证页面对用户的响应。    
WorkerGlobalScope作用域下的常用属性、方法如下:
    1、self  我们可以使用 WorkerGlobalScope 的 self 属性来或者这个对象本身的引用
    2、location 属性返回当线程被创建出来的时候与之关联的 WorkerLocation 对象,
    它表示用于初始化这个工作线程的脚步资源的绝对 URL,
    即使页面被多次重定向后,这个 URL 资源位置也不会改变。
    3、close   关闭当前线程,与terminate作用类似
    4、importScripts   我们可以通过importScripts()方法通过url在worker中加载库函数
    5、XMLHttpRequest  有了它,才能发出Ajax请求
    6setTimeout/setInterval以及addEventListener/postMessage


关于worker    我们可以做什么:

   1.可以加载一个JS进行大量的复杂计算而不挂起主进程,并通过postMessage,onmessage进行通信
  2.可以在worker中通过importScripts(url)加载另外的脚本文件
  3.可以使用 setTimeout(), clearTimeout(), setInterval(), and clearInterval()
  4.可以使用XMLHttpRequest来发送请求
  5.可以访问navigator的部分属性

局限性:

  1.不能跨域加载JS
  2.worker内代码不能访问DOM
  3.各个浏览器对Worker的实现不大一致,
    例如FF里允许worker中创建新的worker,而Chrome中就不行
  4.IE这个新特性

Js单线程


<script>
      //添加到任务队列中,待同步任务所处的‘执行栈’执行完毕,1秒后执行任务队列中的这个匿名函数
       setTimeout(function(){
           console.log('come on');
       },1000);
       //只要不关闭该alert,‘执行栈’就没结束,从而也就不会进入到任务   "队列  " 中
       alert('waiting');
   </script>

创建一个Worker对象

  <script>
    function init(){
        //创建一个Worker对象,并向它传递将在新线程中执行的脚本url
        var worker = new Worker('worker.js');
        //接收worker传递过来的数据
        worker.onmessage = function(event){         document.getElementById('result').
        innerHTML+= event.data
        };
    };
    </script>
    JS代码
        var i = 0;
    function timedCount(){
        for(var j = 0, sum = 0; j < 100; j++){
            for(var i = 0; i < 100000000; i++){
                sum+=i;
            };
        };
        //将得到的sum发送回主线程
        postMessage(sum);
    };
    //将执行timedCount前的时间,通过postMessage发送回主线程
    postMessage('Before computing, '+new Date());
    timedCount();
    //结束timedCount后,将结束时间发送回主线程
    postMessage('After computing, ' +new Date());

terminate onerror

(function init() {
    var worker = new Worker('worker.js');
    //每隔100毫秒,向子线程传递{name: 'monkey'}信息
    setInterval(function() {
        worker.postMessage({
            name: 'monkey'
        });
    }, 1000);

    //当主线程worker收到来自子线程的消息后,触发message事件
    worker.onmessage = function(event) {
        document.getElementById('result').innerHTML += event.data + "<br/>";
        //主线程使用terminate方法中断与子线程来往,在浏览器中只能显示一次event.data
        worker.terminate();
    };

    worker.onerror = function(e) {
        //打印出错消息
        console.log(e.message);
        //中断与子线程的联系
        worker.terminate();
    }
})();

    wokers.js
    alert("asdf");
    onmessage = function(event){
       postMessage(event.data.name);
    };

报错原因是alert为window对象的方法,所以会报错undefined。
worker.js执行的上下文,与主页面html执行时的上下文并不相同,
最顶层的对象并不是window,woker.js执行的全局上下文,是个叫做WorkerGlobalScope的东东,
所以无法访问window、与window相关的DOM API,但是可以与setTimeout、setInterval等协作。

snow

<!DOCTYPE html>
<html>
<head>
    <meta charset="UTF-8">
    <title></title>
    <style type="text/css">
        body,html{
            height: 100%;
        }
    </style>
</head>
<body>
<script type="text/javascript">
    var i = 0;
    var sw = new Worker("snowWorker.js");
    sw.onmessage = function (e) {
        if(e.data < 0){
            //worker 发送-1的时候是 创建雪花
            createSnow(i);
            //通知worker开始 计算下落
            sw.postMessage(i);
            i++;
        }else{
            //雪花下落
            snowDown(e.data);
        }
    }

    //创建一个雪花
    function createSnow(id){
        var one = document.createElement("div")
        var cha = document.body.clientWidth - one.offsetWidth
        var rand = Math.floor(Math.random() * cha)
        document.body.appendChild(one)
        one.style.position = "absolute";
        one.style.top = "-10px";
        one.style.zIndex = "5000px";
        one.style.fontSize = "40px";
        one.style.left = rand + "px";
        one.innerHTML = "❄";
        one.id = id;
    }

    //雪花下落
    function snowDown (id) {
        var a = document.getElementById(id);
        a.style.top = a.offsetTop + 5 +"px"
        if (a.offsetTop > document.body.clientHeight) {
            document.body.removeChild(a);
            sw.postMessage("r" + id);
        }
    }
</script>
</body>
</html>
//每过200毫秒通知前台页面产生一个雪花
setInterval(function(){
    self.postMessage(-1);
},200);

var interArray = [];

//前台页面雪花产生之后,将id发送给worker,同时worker开启一个计时器,每过50毫秒通知前台,雪花位置移动
self.onmessage = function(e){
    var msg = e.data.toString();

     //  msg.indexOf('r')  字符串中找不到r  为 -1;找到则返回相应的位置                                    
    if(msg.indexOf('r') != -1){
        clearInterval(interArray[parseInt(msg.replace("r",""))]);
        //console.log(msg);
    }else{
        interArray[msg] = setInterval(function(){
            this.postMessage(msg);
        },50);
    }
}
评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值