防抖和节流是防止高频率触发的事件
防抖,一般用在使用
onresize事件(onresize:当浏览器被重置大小时执行Javascript代码)、
oninput事件:在用户输入时触发。
如果事件进行高频率触发,很可能会导致服务器崩溃
那么就可以使用函数防抖进行优化,比如你乘坐电梯,如果十秒钟之内有人进入或者出去,那么十秒钟就会重新开始计时,直到十秒之内都不在有人流动才会关门
那么节流就不一样了:同样是电梯十秒运作,电梯的机制是当人进入电梯 后,十秒钟内自动关门,这十秒钟内人可以进出,当到了十秒钟后,不管你有没有人进入出去都直接关门,准时运作。
函数节流简单理解
每隔一段时间执行一次
函数防抖简单理解
每当事件触发一次,就会重置定时器,一直到最后一次触发事件,再去执行
防抖一般用于触发input事件
例如:
<body>
请输入信息:<input type="text">
<script>
var input =document.querySelector('input');
input.oninput = function(){
console.log('事件被触发');
}
</script>
</body>
效果如下:
我们在输入文字时,每次输入都会发送请求,这样中间的很多东西没有必要给后端,给了的话对服务器的压力非常大,那么在这里可以使用函数防抖来进行优化
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
</head>
<body>
<input type="text">
<script>
var input = document.querySelector('input');
function debounce(callBack, time) {
var timer = null;
return function () {
if (timer) {
clearTimeout(timer)
}
timer = setTimeout(callBack,time);
}
}
function fn2() {
console.log('防抖');
}
input.addEventListener('input',debounce(fn2,1000))
</script>
</body>
</html>
进行优化过后:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>防抖优化</title>
</head>
<body>
请输入信息:<input type="text">
<script>
var processor = {
timeoutId: null,
performProcessing: function() {
var days = new Date()
var a= days.getHours();
var b= days.getMonth();
var c= days.getSeconds();
var d= days.getMilliseconds();
console.log(a+'时'+b+'分'+c+'秒'+d+'毫秒');
},
process: function() {
var that = this;
clearTimeout(that.timeoutId);
that .timeoutId = setTimeout(function() {
that.performProcessing();
}, 500) //每隔500毫秒后执行,如果中间间隔没到五秒钟还在输入,那么这500毫秒将重新开始计算
}
};
document.querySelector('input').oninput = function() {
processor.process();
}
</script>
</body>
</html>
效果如下图所示:
节流
原理:规定一个时间,在这个时间段内的所有事件都会一起被执行
一般用于:resize
,touchmove
移动DOM,上拉列表加载数据等
例如:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<meta http-equiv="X-UA-Compatible" content="IE=edge">
<meta name="viewport" content="width=device-width, initial-scale=1.0">
<title>Document</title>
</head>
<body>
<input type="text">
<script>
var input = document.querySelector('input');
function fn1(callback,time){
var flag = true;
return function(){
if (flag) {
flag = false;
callback();
setTimeout(()=>{
flag = true
},time)
}
}
}
function fn2(){
console.log('节流');
}
input.addEventListener('input',fn1(fn2,1000))
</script>
</body>
</html>
效果为每个一秒节流一次
扩展例子如下:
<body>
<div>
加入节流-定时器 & 时间戳:<input type="text" id="throttle"/>
</div>
<script>
window.onload = () => {
function ajax (data) {
console.log(new Date().toLocaleTimeString() + ' - ' + data)
}
function throttle(fn, delay) {
let last
return args => {
let now = Date.now()
if (last && now < last + delay) {
clearTimeout(fn.id)
fn.id = setTimeout(() => {
fn.call(this, args)
last = now
}, delay)
} else {
fn.call(this, args)
last = now
}
}
}
const throttleAjax = throttle(ajax, 1000)
document.querySelector('#throttle').addEventListener('keyup', e => {
throttleAjax(e.target.value)
})
}
</script>
</body>