函數防抖,就是指觸發事件後在 n 秒內函數只能執行一次,若是在 n 秒內又觸發了事件,則會從新計算函數執行時間。app
簡單的說,當一個動做連續觸發,則只執行最後一次。函數
打個比方,坐公交,司機須要等最後一我的進入才能關門。每次進入一我的,司機就會多等待幾秒再關門。工具
限制一個函數在必定時間內只能執行一次。性能
舉個例子,乘坐地鐵,過閘機時,每一個人進入後3秒後門關閉,等待下一我的進入。this
爲了方便理解,咱們首先經過一個可視化的工具,感覺一下三種環境(正常狀況、函數防抖狀況 debounce、函數節流 throttle)下,對於mousemove事件回調的執行狀況。code
豎線的疏密表明事件執行的頻繁程度。能夠看到,正常狀況下,豎線很是密集,函數執行的很頻繁。而debounce(函數防抖)則很稀疏,只有當鼠標中止移動時纔會執行一次。throttle(函數節流)分佈的較爲均已,每過一段時間就會執行一次。事件
連續的事件,只需觸發一次回調的場景有:資源
間隔一段時間執行一次回調的場景有:it
函數防抖的簡單實現:ast
const _.debounce = (func, wait) => { let timer; return () => { clearTimeout(timer); timer = setTimeout(func, wait); }; };
函數防抖在執行目標方法時,會等待一段時間。當又執行相同方法時,若前一個定時任務未執行完,則 clear 掉定時任務,從新定時。
1)函數節流的 setTimeout 版簡單實現
const _.throttle = (func, wait) => { let timer; return () => { if (timer) { return; } timer = setTimeout(() => { func(); timer = null; }, wait); }; };
函數節流的目的,是爲了限制函數一段時間內只能執行一次。所以,經過使用定時任務,延時方法執行。在延時的時間內,方法若被觸發,則直接退出方法。從而,實現函數一段時間內只執行一次。
2)函數節流的時間戳版簡單實現 根據函數節流的原理,咱們也能夠不依賴 setTimeout實現函數節流。
const throttle = (func, wait) => { let last = 0; return () => { const current_time = +new Date(); if (current_time - last > wait) { func.apply(this, arguments); last = +new Date(); } }; };
其實現原理,經過比對上一次執行時間與本次執行時間的時間差與間隔時間的大小關係,來判斷是否執行函數。若時間差大於間隔時間,則馬上執行一次函數。並更新上一次執行時間。
相同點:
不一樣點: