文章目录
1. 前言
首先来举个例子。百度首页的百度输入框,用户输入的时候,每次输入的信息,我们都能看到百度服务器返回给我们的联想关键字。我们每改动一个字,它就换一次联想词,这是我们肉眼能看到的速度,实际上如果不加以处理,可能已经上服务器发起了好几十次的同一个关键字联想请求了,具体速度依赖于不同的pc等机器上的运行速度不同。那么,刚刚也谈到,对于同一个关键字,请求这么多次,也许想给用户呈现的就一次,剩下的请求都是浪费的,并且如果成千上万甚至上亿的用户同时请求,对服务器的负担是巨大的。
防抖节流解决的问题:
在连续触发的事件中,事件处理函数的频繁调用会加重浏览器或服务器的性能负担导致用户体验糟糕,有哪些连续触发的事件呢 ?
比如,浏览器滚动条的滚动事件、浏览器窗口调节的resize事件、输入框内容校验以及在移动端的touchmove事件等。
所以,我们将采用防抖函数(debounce )和节流函数(throttle)来限制事件处理函数的调用频率。
总的来说:防抖函数(debounce )和节流函数(throttle)是在时间轴上控制函数的执行次数。
2. 函数防抖(debounce)
延迟防抖
延迟防抖(debounce): 在事件被触发n秒后再执行回调,如果在这n秒内又被触发,则重新计时。
生活中的实例: 如果有人进电梯(触发事件),那电梯将在10秒钟后出发(执行事件监听器),这时如果又有人进电梯了(在10秒内再次触发该事件),我们又得等10秒再出发(重新计时)。
当持续触发事件时,一定时间段内没有再触发事件,事件处理函数才会执行一次。
如果设定的时间到来之前,又一次触发了事件,就重新开始延时。
如下图,持续触发click事件时,并不执行handle函数,当1000毫秒内没有触发click事件时,才会延时触发click事件。
前缘防抖
执行动作在前,然后设定周期,周期内有事件被触发,不执行动作,且周期重新设定。
为什么要这样呢?
试想第一种延迟debounce,我们本来想对用户输入的关键字,发起请求联想的频率降低,但是如果用户在我们设定的时间中,一直输入,导致的就是,用户一直看不到关键字,我们倒不如第一次输入的时候就发起一个请求,服务器返回结果,呈现给用户,然后后续用户的键入结束在继续请求)。
<!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>
<button id="debounce1">点我防抖呐!</button>
<script>
function handle() {
console.log("防抖成功!"