首頁 >web前端 >js教程 >詳解javascript進階計時器_javascript技巧

詳解javascript進階計時器_javascript技巧

WBOY
WBOY原創
2016-05-16 15:22:421569瀏覽

setTimeout()和setInterval()可以用來建立定時器,其基本的用法這裡就不再做介紹了。這裡主要介紹一下javascript的程式碼佇列。在javascript中沒有任何程式碼是立即執行的,一旦進程空閒就盡快執行。所以說定時器中設定的時間不代表執行時間就一定相符,而是代表代碼會在指定時間間隔後加入佇列等待。如果在這個時間點上,佇列中沒有其他東西,那麼這段程式碼就會被執行,表面上看起來好像程式碼就在精確指定的時間點上執行了。所以就會產生一些問題。

重複定時器

通常,我們使用setInterval方法來以相同時間間隔重複執行某段程式碼。但是使用該方法會有兩個問題:第一個是某些間隔會被跳過;第二個就是多個定時器的程式碼執行之間的間隔可能會比預期的小。
在這裡,我們來舉個例子:如果某個onclick事件處理程序使用setInterval設定了一個200ms間隔的重複定時器,如果事件處理程序花了300ms的時間完成,就會跳過一個時間間隔同時運行一個定時器代碼。
我們也可以透過下面的程式碼來得到結論:

//重复定时器
var i =0;
setInterval(function(){
 //如果事件处理时间长于间隔时间
 i++;
 for(var j=0;j<100000000;j++){}
 document.write(i+' ');
},100);
//可以明显感觉到时间间隔不相等
为了避免这种时间间隔的问题,我们可以采用链式调用setTimeout方法来取代setInterval。

//可以采用链式调用setTimeout来取代setInterval
var i = 0;
setTimeout(function(){
 //处理内容
 i++;
 for(var j=0;j<100000000;j++){}
 document.write(i+' ');
 //
 setTimeout(arguments.callee,100);
},100);
//这样处理效果明显好多了。

每次函數執行的時候都會建立一個新的計時器,第二個setTimeout呼叫使用了arguments.callee來取得目前執行的函數的引用,並為其設定另一個計時器。這樣做是為了在前一個定時器代碼執行完之前,不會向隊列插入新的定時器代碼,確保不會有任何缺失的間隔,也保證了在下一次定時器代碼執行之前,至少要等待指定的間隔,避免了連續的運轉。可謂一舉兩得,現在主流框架中的動畫一般都是這樣來實現重複定時的。

函數節流

定時器不只是用來定時的,也可以用來緩解瀏覽器的壓力。瀏覽器中某些計算和處理要比其他的昂貴很多,比如說DOM操作,就會需要更多的記憶體和CPU時間,連續使用過多的DOM操作可能會導致瀏覽器掛起,甚至崩潰。
函數節流的基本想法就是,某些程式碼不可以在沒有間斷的情況連續重複執行。第一次呼叫函數,建立一個定時器,在指定的時間間隔之後執行程式碼。當第二次呼叫函數時,它會清除前一次的計時器並設定一個。目的就是為了在執行函數的請求停止一段時間後再執行。
程式碼如下:

//再来谈谈函数节流
function throttle(method,context){
 clearTimeout(method.tId);
 method.tId = setTimeout(function(){
  method.call(context);
 },100);
}
//该函数接受两个参数,第一个是要执行的函数,第二个是作用域。
//使用方法demo
//未使用情况:
window.onresize = function(){
 var div = document.getElementByTagName(body);
 div.style.height = div.offsetWidth +'px';
}
//使用情况;
function resizeDiv(){
 var div = document.getElementByTagName(body);
 div.style.height = div.offsetWidth +'px';
}
window.onresize = function(){
 throttle(resizeDiv);
};
//只要代码是周期性执行的,都应该使用节流。

這樣給使用者的感覺並不會很大,確是給瀏覽器減少了不少的壓力,函數節流也是許多框架常用的技巧之一。

以上就是關於javascript高階定時器的相關介紹,希望對大家的學習有所幫助。

陳述:
本文內容由網友自願投稿,版權歸原作者所有。本站不承擔相應的法律責任。如發現涉嫌抄襲或侵權的內容,請聯絡admin@php.cn