节流和防抖都是通过降低事件执行的频率而达到节省资源的效果
节流
一段时间只执行一次,多少秒之后获取验证码、resize 事件和scroll 事件等
类似王者荣耀中的传送,一段时间内只能传送一次,具体实现如下:
function throttle(fn, delay) {
let lastTime = 0;
return function () {
let currentTime = Date.now();
if (currentTime - lastTime > delay) {
lastTime = currentTime;
fn.apply(this, arguments);
}
};
}
防抖
一段时间内连续触发事件,只执行最后一次,如搜索,手机号、邮箱地址的校验
类似王者荣耀中的回城操作,如果被打断则重新计时,不打断则执行最后一次操作。
代码实现如下:
function debounce(fn, delay) {
let timer = null;
return function () {
if (timer) {
clearTimeout(timer);
}
timer = setTimeout(() => {
fn.apply(this, arguments);
}, delay);
};
}
具体应用实现如下:
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8" />
<meta name="viewport" content="width=device-width, initial-scale=1.0" />
<title>Document</title>
<style>
.box {
width: 100px;
height: 100px;
background-color: blue;
}
</style>
</head>
<body>
<div class="box"></div>
<input class="input" />
<script>
const domBox = document.querySelector(".box");
const domIpt = document.querySelector(".input");
console.log("🚀 ~ file: 节流.html:20 ~ domBox:", domBox);
function throttle(fn, delay) {
let timer = null;
return function () {
if (timer) {
clearTimeout(timer);
timer = null;
}
timer = setTimeout(() => {
// fn.apply(this, arguments);
fn.call(this, ...arguments);
}, delay);
};
}
// 节流一段时间只执行一次,多少秒之后获取验证码、resize 事件和scroll 事件等
function throttle(fn, delay) {
let lastTime = 0;
return function () {
let currentTime = Date.now();
if (currentTime - lastTime > delay) {
lastTime = currentTime;
fn.apply(this, arguments);
}
};
}
// 防抖:一段时间内连续触发事件,只执行最后一次,如搜索,手机号、邮箱地址的校验
function debounce(fn, delay) {
let timer = null;
return function () {
if (timer) {
clearTimeout(timer);
}
timer = setTimeout(() => {
fn.apply(this, arguments);
}, delay);
};
}
domBox.addEventListener(
"click",
throttle(e => {
console.log("click dom box", e);
}, 1000)
);
domIpt.addEventListener(
"input",
debounce(function (event) {
console.log("debounce event =>", event);
}, 500)
);
</script>
</body>
</html>