js 定时器

来源:互联网 发布:手机编写c语言的软件 编辑:程序博客网 时间:2024/04/30 22:55

js定时器操作,setTimeout clearTimeout setInterval clearInterval

浏览器的js为单线程,那他是怎么处理这样的情况的呢?定时器操作是异步的,也就是浏览器有专门的线程在处理,在js代码中调用的只是浏览器中对应的线程。当浏览器的定时器线程处理完成后,将回调函数压入任务队列,等待执行。

for(int i=0;i<1000;i++){    setTimeout(function(){        console.log(new Date,i);    },1000);}

在上述例子中,最后输出的,i始终都为1000,因为同步代码先执行,也就是for语句,再因为闭包的原因,他们引用的是同一个地址的i,当同步代码执行完成时i的值在内存中为1000;在时间上,输出按照几百个为时间大致相同的一组输出,这是因为异步队列和任务队列也有数量限制,在队列满时,其他等待。一组内的时间又相差不大的原因,是因为它们几乎同时执行。这里不是应该1秒执行一次吗?我们要再次解读定时器这个东西?手机里设置的倒计时的定时器,实在按下开始的那一瞬间就开始计时的。这里也一样,定时器是在被调用的那一瞬间开始执行的,也就是在for循环调用到setTimeout的那一瞬间开始计时,1秒后将回调函数加入任务队列,而for循环是同步代码,会连续执行,代码执行速率是非常快的,以至于每次调用到定时器的时候时间也相差无几,在相差无几的开始时间计时一样的时间,那结束时间也就相差无几,那他们被添加进任务队列的时间也相差无几,所以最后被执行的时候也相差无几。总结出来就是一句话,循环在几乎相同的时间设置了n个相同的定时器,这些定时器也几乎在同一时间结束。如何解决?在每次回调被准确执行的时候再设置下一个。
如:

    //加一个闭包解决输出i的问题,因为在加了一个自执行的函数之后,相当于创造一个函数作用域,在传值的时候创建了i的一个副本。    for(int i=0;i<1000;i++){    (function(i){setTimeout(function(){        console.log(i);    },1000);    })(i);    }
(function(){ //这个闭包为解决全局变量i污染的问题,把它变成局部变量        var i=0;        (function a(){//只为自执行            setTimeout(function(){                console.log(i);                i++;                if(i<10)                {                    a();//执行下一次定时                }            },1000)        })();    })();
0 0
原创粉丝点击