名詞解釋:在事件被觸發n秒後再執行回調函數,若是在這n秒內又被觸發,則從新計時。javascript
使用場景:以百度輸入框例,好比你要查詢XXx,想實現輸完了XXx以後,再進行搜索請求,這樣能夠有效減小請求次數,節約請求資源。java
函數防抖簡單實現ajax
<script type="text/javascript"> window.onload = function () { function ajax(content) {//模擬ajax請求 console.log('ajax request ' + content) } function debounce(fun, delay) { return function (arguments) { //獲取函數的做用域和變量 let that = this; let args = arguments; clearTimeout(fun.id)// 清除定時器 fun.id = setTimeout(function () { fun.call(that, args ) }, delay) } } let debounceAjax = debounce(ajax, 1000) XXX.addEventListener('keyup', function (e) { debounceAjax(e.target.value) }) } </script>
名詞解釋:連續執行函數,每隔必定時間執行函數。規定一個單位時間,在這個單位時間內,只能有一次觸發事件的回調函數執行,若是在同一個單位時間內某事件被觸發屢次,只有一次能生效。app
使用場景:鼠標連續屢次click事件,mousemove 事件,監聽滾動事件,好比是否滑到底部自動加載更多等等...函數
函數節流簡單實現性能
function throttle(fn, delay) { let lastTime; let timer; delay || (delay = 300); // 默認間隔爲300ms return function(arguments) { let context = this; let args = arguments; let nowTime = +new Date(); // 獲取系統當前的時間 if (lastTime && nowTime < lastTime+ delay) { // 當前距離上次執行的時間小於設置的時間間隔 clearTimeout(timer); // 清除定時器 timer = setTimeout(function() { // delay時間後,執行函數 lastTime= nowTime ; fn.apply(context, args); }, delay); } else { // 當前距離上次執行的時間大於等於設置的時間,直接執行函數 lastTime= nowTime ; fn.apply(context, args); } }; }
能夠用平常進入電梯來舉例,形象地描述節流和防抖的區別優化
函數防抖:若是A在10:00:00開門走入電梯內(觸發事件),若是後續沒有人進入電梯,電梯將在5秒鐘以後10:00:05關門(執行事件監聽器)。這時若是B在10:00:04走入電梯內,電梯會在10:00:09才關門。this
函數節流 :若是A在10:00:00開門走入電梯內(觸發事件),若是後續沒有人進入電梯,電梯將在5秒鐘以後10:00:05關門(執行事件監聽器)。這時若是B在10:00:04走入電梯內,電梯一樣是在10:00:05關門。這個時間從第一我的進入電梯開始計時,無論在5秒以內進來多少人,電梯都會在10:00:05關門。若是一直沒有人進來,則電梯不運行。code
根據實際業務場景,合理的利用debounce(防抖)和throttle(節流)能夠優化性能和提升用戶體驗。事件
效果:
函數防抖是某一段時間內只執行一次;
函數節流是間隔時間執行,無論事件觸發有多頻繁,都會保證在規定時間內必定會執行一次真正的事件處理函數。
原理:防抖是維護一個計時器,規定在delay時間後觸發函數,可是在delay時間內再次觸發的話,都會清除當前的 timer 從新計時。這樣一來,只有最後一次操做事件才被真正觸發。節流是經過判斷是否到達必定時間來觸發函數,若沒到規定時間則使用計時器延後,而下一次事件則會從新設定計時器。