這期內容當中小編將會給大家帶來有關JavaScript中節流和防抖的區別是什么,文章內容豐富且以專業的角度為大家分析和敘述,閱讀完這篇文章希望大家可以有所收獲。
按照設定的時間固定執行一次函數,比如200ms一次。注意:固定就是你在mousemove過程中,執行這個節流函數,它一定是200ms(你設定的定時器延遲時間)內執行一次。沒到200ms,一定會返回,沒有執行回調函數的。
主要應用場景有:scroll、touchmove
抖動停止后的時間超過設定的時間時執行一次函數。注意:這里的抖動停止表示你停止了觸發這個函數,從這個時間點開始計算,當間隔時間等于你設定時間,才會執行里面的回調函數。如果你一直在觸發這個函數并且兩次觸發間隔小于設定時間,則一定不會到回調函數那一步。 ·
主要應用場景有:input驗證、搜索聯想、resize
思路: 第一次先設定一個變量true,第二次執行這個函數時,會判斷變量是否true,是則返回。當第一次的定時器執行完函數最后會設定變量為flase。那么下次判斷變量時則為flase,函數會依次運行。
代碼一:首次不執行
function throttle(fn,delay=100){
//首先設定一個變量,在沒有執行我們的定時器時為null
let timer = null;
return function(){
//當我們發現這個定時器存在時,則表示定時器已經在運行中,需要返回
if(timer) return;
timer = setTimeout(()=>{
fn.apply(this,arguments);
timer = null;
},delay);
}
}代碼二:首次執行
function throttle2(fn,delay=100){
let last = 0;
return function(){
let curr = +new Date();
if(curr - last > delay){
fn.apply(this,arguments);
last = curr;
}
}
}思路:首次運行時把定時器賦值給一個變量,第二次執行時,如果間隔沒超過定時器設定的時間則會清除掉定時器,重新設定定時器,依次反復,當我們停止下來時,沒有執行清除定時器,超過一定時間后觸發回調函數。
代碼一:首次不執行
function debounce(fn,delay=200){
let timer = null;
return function(){
if(timer) clearTimeout(timer);
timer = setTimeout(()=>{
fn.apply(this,arguments);
timer = null;
},delay);
}
}代碼二:首次執行
function debounce2(fn, delay = 200, atBegin = true) {
let timer = null, last = 0,during;
return function () {
let self = this, args = arguments;
var exec = function () {
fn.apply(self, args);
}
if (atBegin && !timer) {
exec();
atBegin = false;
} else {
during = Date.now() - last;
if (during > delay) {
exec();
} else {
if (timer) clearTimeout(timer);
timer = setTimeout(function () {
exec();
}, delay);
}
}
last = Date.now();
}
}演示 打開控制臺觀察變化
上面的代碼只是我自己的一個簡單實現,看看lodash里面的兩個核心實現代碼。生產中建議使用它們的庫,畢竟有這么多人在用,出bug的機會比較少,我上面的代碼有可能有一些情況沒考慮到。如果你發現有問題的,也請告訴我。
如果在項目中有需要用到的,可以直接安裝單個的NPM模塊。 throttle 和 debounce
lodash庫里面這兩個函數設置的參數有點復雜,記錄一下里面的參數和代碼使用。
官方文檔解釋:
創建一個節流函數,在 wait 秒內最多執行 func 一次的函數。 該函數提供一個 cancel 方法取消延遲的函數調用以及 flush 方法立即調用。 可以提供一個 options 對象決定如何調用 func 方法, options.leading 與|或 options.trailing 決定 wait 前后如何觸發。 func 會傳入最后一次傳入的參數給這個函數。 隨后調用的函數返回是最后一次 func 調用的結果。
注意: 如果 leading 和 trailing 都設定為 true 則 func 允許 trailing 方式調用的條件為: 在 wait 期間多次調用。
如果 wait 為 0 并且 leading 為 false, func調用將被推遲到下一個點,類似setTimeout為0的超時。
參數
func (Function) 要節流的函數 [wait=0] (number) 需要節流的毫秒 [options] (Object) 選項對象 [options.leading=true] (boolean) 指定調用在節流開始前 [options.trailing=true] (boolean) 指定調用在節流結束后
返回值 (Function)
返回節流的函數
示例
// 避免在滾動時過分的更新定位
jQuery(window).on('scroll', _.throttle(updatePosition, 100));
// 點擊后就調用 `renewToken`,但5分鐘內超過1次。
var throttled = _.throttle(renewToken, 300000, { 'trailing': false });
jQuery(element).on('click', throttled);
// 取消一個 trailing 的節流調用
jQuery(window).on('popstate', throttled.cancel);創建一個 debounced(防抖動)函數,該函數會從上一次被調用后,延遲 wait 毫秒后調用 func 方法。 debounced(防抖動)函數提供一個 cancel 方法取消延遲的函數調用以及 flush 方法立即調用。 可以提供一個 options(選項) 對象決定如何調用 func 方法,options.leading 與 options.trailing 決定延遲前后如何觸發(先調用后等待 還是 先等待后調用)。 func 調用時會傳入最后一次提供給 debounced(防抖動)函數 的參數。 后續調用的 debounced(防抖動)函數返回是最后一次 func 調用的結果。
注意: 如果 leading 和 trailing 選項為 true, 則 func 允許 trailing 方式調用的條件為: 在 wait 期間多次調用防抖方法。
如果 wait 為 0 并且 leading 為 false, func調用將被推遲到下一個點,類似setTimeout為0的超時。
參數
<pre>//code from http://caibaojian.com/throttle-debounce.html `func (Function) 要防抖動的函數 [wait=0] (number) 需要延遲的毫秒數 [options] (Object) 選項對象 [options.leading=false] (boolean) 指定調用在延遲開始前 [options.maxWait] (number) 設置 func 允許被延遲的最大值 [options.trailing=true] (boolean) 指定調用在延遲結束后` </pre>
返回值 (Function)
返回具有防抖動功能的函數
示例
// 避免窗口在變動時出現昂貴的計算開銷。
jQuery(window).on('resize', _.debounce(calculateLayout, 150));
// 當點擊時 `sendMail` 隨后就被調用。
jQuery(element).on('click', _.debounce(sendMail, 300, {
'leading': true,
'trailing': false
}));
// 確保 `batchLog` 調用1次之后,1秒內會被觸發。
var debounced = _.debounce(batchLog, 250, { 'maxWait': 1000 });
var source = new EventSource('/stream');
jQuery(source).on('message', debounced);
// 取消一個 trailing 的防抖動調用
jQuery(window).on('popstate', debounced.cancel);上述就是小編為大家分享的JavaScript中節流和防抖的區別是什么了,如果剛好有類似的疑惑,不妨參照上述分析進行理解。如果想知道更多相關知識,歡迎關注億速云行業資訊頻道。
免責聲明:本站發布的內容(圖片、視頻和文字)以原創、轉載和分享為主,文章觀點不代表本網站立場,如果涉及侵權請聯系站長郵箱:is@yisu.com進行舉報,并提供相關證據,一經查實,將立刻刪除涉嫌侵權內容。