在本文中,我们将讨论 JavaScript 防抖(Debouncing) 方法及其实现。

什么是防抖?

防抖是一种在 JavaScript 中用于提高浏览器性能的方法。网页上可能有一些需要耗时计算的特性。如果经常应用此类方法,可能会严重影响浏览器的性能,因为 JavaScript 是一种单线程语言。防抖是一种编程技术,确保耗时的活动不会触发网页性能下降。换句话说,防抖方法在调用时不会运行。相反,它们会等待一段预定的时间才执行。当我们再次调用相同的过程时,会取消上一个过程,并重新设置计时器。

防抖是节流的近亲,它们都有助于改善 Web 应用程序的性能。尽管如此,它们在不同的情况下发挥作用。当我们只考虑最终状态时,可以使用防抖。例如,它们会等到用户完成输入以获取输入建议的搜索结果。如果我们想以规定的速度管理所有中间状态,那么节流是最好的工具。

防抖的实现

让我们通过一个示例来看看如何实现防抖方法。

const debounce = (func, wait) => {
  let timeout;
  return function mainFunction(...args) {
    const later = () => {
      clearTimeout(timeout);
      func(...args);
    };
    clearTimeout(timeout);
    timeout = setTimeout(later, wait);
  };
};

防抖函数是一个返回另一个函数的高阶函数。它用于在 funcwait 函数参数和 timeout 变量 周围创建闭包以保存它们的值。以下变量的定义如下:

  • func:我们希望在防抖时间后执行的函数。
  • wait:在上一个操作后,防抖函数可以等待执行 func 的时间。
  • timeout:timeout 函数是一个用于指示运行防抖的值。

示例:

让我们通过示例来理解 JavaScript 中的防抖方法。在下面的示例中,一个按钮与事件监听器相连接,该监听器调用防抖函数。在下面的示例中,防抖函数有两个参数:一个 函数 和一个 数字(时间)。声明了一个 计时器,如其名称所示,它会在一定的时间后调用防抖函数。

<!DOCTYPE html>
<html>
<head>
  <title>JavaScript Debouncing</title>
</head>
<body>
  <h1>JavaScript Debounce</h1>
  <input type="button" id="debounce" value="Click Here">
  <script>
    var button = document.getElementById("debounce");
    const debounce = (func, wait) => {
      let debounceTimer;
      return function() {
        const context = this;
        const args = arguments;
        const later = () => {
          clearTimeout(debounceTimer);
          func.apply(context, args);
        };
        clearTimeout(debounceTimer);
        debounceTimer = setTimeout(later, wait);
      };
    };
    button.addEventListener('click', debounce(function() {
      alert("Hello\nThis message will be displayed after 3 seconds, and no matter how many times we click the button.");
    }, 3000));
  </script>
</body>
</html>

输出: 执行上述代码后,我们将得到以下输出:

1.png

正如我们在上面的截图中看到的,有一个 "Click here" 按钮。当点击 "Click here" 按钮时,它会显示一个警告框,显示一个警告消息。该功能每次更新时都会更新,这意味着如果在延迟时间(4 秒)之前按下按钮,则会清除初始计时器并启动一个新的计时器。使用 clearTimeOut() 函数来完成此任务。

2.png

带有立即执行函数的防抖函数的实现

下面的防抖实现返回一个函数,只要被调用,就不会被调用。在N 毫秒的不活动后,该函数将再次被调用。当将初始函数作为参数调用函数时,它立即调用函数,并在调用之前等待一段时间间隔。

function debounce(func, wait, immediate) {
  var timeout;
  return function mainFunction() {
    var context = this;
    var args = arguments;
    var later = function() {
      timeout = null;
      if (!immediate) func.apply(context, args);
    };
    var callNow = immediate && !timeout;
    clearTimeout(timeout);
    timeout = setTimeout(later, wait);
    if (callNow) func.apply(context, args);
  };
}

防抖返回一个函数,该函数可以在传递函数的事件监听器上传递。

var returnedFunction = debounce(function() {
}, 3000);
window.addEventListener('resize', returnedFunction);

示例:

让我们通过示例来理解带有立即执行函数的防抖函数的用法。

<!DOCTYPE html>
<html>
<head>
  <title>JavaScript Debouncing</title>
</head>
<body>
  <h1>JavaScript Debounce</h1>
  <button id="debounce">Click here</button>
  <script>
    var button = document.getElementById("debounce");
    const debounce = (func, wait, immediate) => {
      var timeout;
      return function executedFunction() {
        var context = this;
        var args = arguments;
        var later = function() {
          timeout = null;
          if (!immediate) func.apply(context, args);
        };
        var callNow = immediate && !timeout;
        clearTimeout(timeout);
        timeout = setTimeout(later, wait);
        if (callNow) func.apply(context, args);
      };
    };
    button.addEventListener('click', debounce(function() {
      alert("This message will be displayed after 3 seconds, and no matter how many times we click the button.");
    }, 3000));
  </script>
</body>
</html>

输出: 执行上述代码后,我们将得到以下输出,如下所示的截图。

3.png

如上面的截图所示,有一个 "Debounce" 按钮。当我们点击 "Debounce" 按钮时,它会显示一个警告消息。如果我们点击 "Ok" 按钮,警告消息将消失。

4.png

应用场景

防抖可用于实现建议文本,我们会等待几秒钟,等用户停止输入后再提供文本建议。因此,在每次按键后等待几秒钟再进行建议。防抖通常用于像 FacebookTwitter 这样的内容加载网站,用户继续滚动。因为有很多视频和照片,如果太频繁地触发滚动事件,会对性能产生影响。因此,在滚动的情况下必须使用防抖。

标签: js, JavaScript, JavaScript语言, JavaScript开发, JavaScript语法, JavaScript脚本, JavaScript教程, JavaScript入门, JavaScript入门教程, JavaScript进阶, JavaScript宝典, JavaScript学习, JavaScript指南, JavaScript大全