溫馨提示×

溫馨提示×

您好,登錄后才能下訂單哦!

密碼登錄×
登錄注冊×
其他方式登錄
點擊 登錄注冊 即表示同意《億速云用戶服務條款》

javascript函數(shù)的節(jié)流和防抖是什么意思

發(fā)布時間:2021-08-20 19:53:11 來源:億速云 閱讀:150 作者:chen 欄目:web開發(fā)

本篇內(nèi)容介紹了“javascript函數(shù)的節(jié)流和防抖是什么意思”的有關(guān)知識,在實際案例的操作過程中,不少人都會遇到這樣的困境,接下來就讓小編帶領(lǐng)大家學習一下如何處理這些情況吧!希望大家仔細閱讀,能夠?qū)W有所成!

防抖和節(jié)流

窗口的resize、scroll,輸入框內(nèi)容校驗等操作時,如果這些操作處理函數(shù)較為復雜或頁面頻繁重渲染等操作時,如果事件觸發(fā)的頻率無限制,會加重瀏覽器的負擔,導致用戶體驗非常糟糕。此時我們可以采用debounce(防抖)和throttle(節(jié)流)的方式來減少觸發(fā)的頻率,同時又不影響實際效果。

這兩個東西都是為了項目優(yōu)化而出現(xiàn)的,官方是沒有具體定義的,他們的出現(xiàn)主要是為了解決一些短時間內(nèi)連續(xù)執(zhí)行的事件帶來性能上的不佳和內(nèi)存的消耗巨大等問題;

像這類事件一般像 scroll keyup mousemove resize等等,短時間內(nèi)不斷的觸發(fā),在性能上消耗是非常大的,尤其是一些改變DOM結(jié)構(gòu)的操作;

節(jié)流[throttle]與防抖[debounce]非常相似,都是讓上述這類事件在規(guī)定的事件從不斷的去觸發(fā)更改成為規(guī)定的時間內(nèi)觸發(fā)多少次;

節(jié)流[throttle]

節(jié)流通俗來解釋就比如我們水龍頭放水,閥門一打開,水嘩嘩的往下流,這個秉著勤儉節(jié)約的優(yōu)良傳統(tǒng)美德,我們要把水龍頭關(guān)小點,最好是如我們心意按照一定規(guī)律在某個時間間隔內(nèi)一滴一滴的往下滴,這,,,好吧這就是我們節(jié)流的概念;

換成函數(shù)來說,使用setTimeout方法,給定兩個時間,后面的時間減去前面的時間,到達我們給定的時間就去觸發(fā)一次這個事件,這么說太籠統(tǒng)的,我們看下面的函數(shù),這里我們以【scroll】為例;

/** 樣式我就順便寫了 **/
<style>
 *{padding:0;margin:0;}
 .scroll-box{
  width : 100%;
  height : 500px;
  background:blue;
  overflow : auto;
 } 
 .scroll-item{
  height:1000px;
  width:100%;
 }
</style>

------------------------

/** 先給定DOM結(jié)構(gòu);**/
<div class="scroll-box">
 <div class="scroll-item"></div>
</div>

------------------------

/**主要看js,為了簡單我用JQ去寫了**/
<script>
 $(document).ready(function(){
  var scrollBox = $('.scroll-box');
  //調(diào)用throttle函數(shù),傳入相應的方法和規(guī)定的時間;
  var thro = throttle(throFun,300);
  //觸發(fā)事件;
  scrollBox.on('scroll' , function(){
   //調(diào)用執(zhí)行函數(shù);
   thro();
  })

  // 封裝函數(shù); 
  function throttle(method,time){
   var timer = null;
   var startTime = new Date();
   return function(){
    var context = this;
    var endTime = new Date();
    var resTime = endTime - startTime;
    //判斷大于等于我們給的時間采取執(zhí)行函數(shù);
    if(resTime >= time){
     method.call(context);
     //執(zhí)行完函數(shù)之后重置初始時間,等于最后一次觸發(fā)的時間
     startTime = endTime;
    }
   }
  }
  function throFun(){
   console.log('success');
  }
 })
</script>

通過以上的函數(shù),我們就可以做到節(jié)流的效果,在規(guī)定的每300毫秒觸發(fā)一次,當然時間可以自定義,根據(jù)需求來;

防抖[debounce ]

寫代碼之前,我們先清楚一下防抖的概念,不知道大家有沒有做過電腦端兩邊懸浮廣告窗口的這么一個東西,當我們拖動滾動條的時候,兩邊的廣告窗口會因為滾動條的拖動,而不斷的嘗試著去居于中間,然后你就會看到這兩個窗口,不停的抖啊抖;

一般這種就叫抖動了,我們要做的就是防止這種抖動,稱為防抖[debounce ];

那這里防抖思想就是當我們拖動完成之后,兩邊的窗口位置再重新去計算,這樣,就會顯得很平滑,看著很舒服了,最主要的操作DOM結(jié)構(gòu)的次數(shù)就大大減少了;

優(yōu)化了頁面性能,降低了內(nèi)存消耗,不然你像IE這種比較老點版本的瀏覽器,說不定就直接給你蹦了

用書面一點的說法就是,在某個事件沒有結(jié)束之前,函數(shù)不會執(zhí)行,當結(jié)束之后,我們給定延時時間,然他在給定的延時時間之后再去執(zhí)行這個函數(shù),這就是防抖函數(shù);

來看代碼:

//將上面的throttle函數(shù)替換為debounce函數(shù);
function debounce(method,time){
 var timer = null ;
 return function(){
  var context = this;
  //在函數(shù)執(zhí)行的時候先清除timer定時器;
  clearTimeout(timer);
  timer = setTimeout(function(){
   method.call(context);
  },time);
 }
}

思路就是在函數(shù)執(zhí)行之前,我們先清除定時器,如果函數(shù)一直執(zhí)行,就會不斷的去清除定時器中的方法,知道我們操作結(jié)束之后,函數(shù)才會執(zhí)行;

其實書寫的方式有很多,主要還是思路的問題,大家寫的多了,自然就知道了;

用途

  1. 當我們做keyup像后臺請求檢驗的時候,可以使用防抖函數(shù),不然我們每按一次鍵盤就請求一次,請求太頻繁,這樣當我們結(jié)束按鍵盤的時候再去請求,請求少很多了,性能自然不用說;

  2. resize 窗口大小調(diào)整的時候,我們可以采用防抖技術(shù)也可以使用節(jié)流;

  3. mousemove 鼠標移動事件我們既可以采用防抖也可以使用節(jié)流;

  4. scroll 滾動條觸發(fā)的事件,當然既可以采用防抖也可以采用節(jié)流;

  5. 連續(xù)高頻發(fā)的事件都可以采用這兩種方式去解決,優(yōu)化頁面性能;

“javascript函數(shù)的節(jié)流和防抖是什么意思”的內(nèi)容就介紹到這里了,感謝大家的閱讀。如果想了解更多行業(yè)相關(guān)的知識可以關(guān)注億速云網(wǎng)站,小編將為大家輸出更多高質(zhì)量的實用文章!

向AI問一下細節(jié)

免責聲明:本站發(fā)布的內(nèi)容(圖片、視頻和文字)以原創(chuàng)、轉(zhuǎn)載和分享為主,文章觀點不代表本網(wǎng)站立場,如果涉及侵權(quán)請聯(lián)系站長郵箱:is@yisu.com進行舉報,并提供相關(guān)證據(jù),一經(jīng)查實,將立刻刪除涉嫌侵權(quán)內(nèi)容。

AI