函数节流与防抖

1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
<!DOCTYPE html>
<html lang="en">
<head>
<meta charset="UTF-8">
<title>防抖和节流</title>
<style>
button {
width: 100px;
height: 50px;
}
.log {
width: 100%;
height: 30px;
border: 1px solid
margin-top: 10px;
}
</style>
</head>
<body>
<button id="debounced">Debounced</button>
<button id="throttled">Throttled</button>
<div id="log1" class="log"></div>
<div id="log2" class="log"></div>

<script>
/*
节流说白了就是每ms执行一次函数,
防抖就是 我最后一次触发后ms后执行一次回调函数
*/
/*debounced(防抖动)函数,该函数会从上一次被调用后,延迟 wait 毫秒后调用 fn 方法。*/
function debounce(fn, wait, options) {
// 等待时间
wait = wait || 0
// 点击次数
let timerId;
console.log("timerId:", timerId);
// 这个函数的功能是:
//
return () {
if (timerId) {
clearTimeout(timerId);
timerId = null;
}
timerId = setTimeout(() {
fn();
}, wait);
console.log("timerId:", timerId);
}
}

// 节流函数,在 wait 秒内最多执行 fn 一次的函数。
function throttle(fn, wait, options) {
wait = wait || 0;
let timerId;
let lastTime = 0;

return () {
let currentTime = new Date();
if (currentTime >= lastTime + wait) {
fn();
lastTime = currentTime;
} else {
if (timerId) {
clearTimeout(timerId);
timerId = null;
}
timerId = setTimeout(() {
fn();
}, wait);
}
}
}

let debouncedBtn = document.getElementById('debounced');
let throttledBtn = document.getElementById('throttled');
let log1 = document.getElementById('log1');
let log2 = document.getElementById('log2');

function handleDebounce() {
log1.innerHTML += 'debounced';
console.log("debounced");
}
function handleThrottle() {
log2.innerHTML += 'throttle';
console.log("throttle");

}
debouncedBtn.addEventListener('click', debounce(handleDebounce, 2000));
throttledBtn.addEventListener('click', throttle(handleThrottle, 2000));
</script>
</body>
</html>