当前位置:   article > 正文

js 函数的防抖(debounce)与节流(throttle)_js debounce

js debounce

目录

序言:

防抖(debounce)

节流(throttle)

 代码示例

附录:

关于节流/防抖函数中 context(this) 的指向解析:

防抖函数中的 this 指向

节流函数中的 this 指向


序言:

我们在平时开发的时候,会有很多场景会频繁触发事件,比如说搜索框实时发请求,onmousemove, resize, onscroll等等,有些时候,我们并不能或者不想频繁触发事件,咋办呢?这时候就应该用到函数防抖和函数节流了!

防抖(debounce)

防抖(debounce)是指在一定时间内,只执行最后一次触发的事件。它适用于那些在连续触发事件的过程中,只关心最后一次触发的结果的情况。

例如,当用户连续输入搜索关键字时,我们可以使用防抖来减少网络请求的次数。在用户停止输入一段时间后,才发送网络请求进行搜索。

下面是一个简单的 JavaScript 实现防抖函数的例子:

  1. function debounce(func, delay) {
  2. let timer;
  3. return function() {
  4. clearTimeout(timer);
  5. timer = setTimeout(() => {
  6. func.apply(this, arguments);
  7. }, delay);
  8. };
  9. }

这个 debounce 函数接受两个参数:func 是要执行的函数,delay 是延迟的时间。在每次触发事件时,它会清除之前设置的定时器,并重新设置一个新的定时器。如果在延迟时间内再次触发事件,定时器会被清除并重新设置。只有在延迟时间结束后没有再次触发事件,才会执行函数。

节流(throttle)

节流(throttle)是指在一定时间内,固定执行事件的频率。它适用于那些在连续触发事件的过程中,需要保持一定的执行频率的情况。

例如,当用户持续滚动页面时,我们可以使用节流来限制处理滚动事件的频率,以避免过多的计算和渲染。

下面是一个简单的 JavaScript 实现节流函数的例子:

  1. function throttle(func, delay) {
  2. let timer;
  3. return function() {
  4. if (!timer) {
  5. timer = setTimeout(() => {
  6. func.apply(this, arguments);
  7. timer = null;
  8. }, delay);
  9. }
  10. };
  11. }

这个 throttle 函数接受两个参数:func 是要执行的函数,delay 是延迟的时间。在每次触发事件时,它会检查是否存在定时器,如果不存在则设置一个新的定时器,并在延迟时间结束后执行函数。这样可以保证在延迟时间内只执行一次函数。

总结起来,防抖和节流都是用于优化性能和控制事件触发频率的技术。防抖适用于只关心最后一次触发结果的情况,而节流适用于需要保持一定执行频率的情况。

 代码示例

  1. <!DOCTYPE html>
  2. <html>
  3. <head>
  4. <meta charset="utf-8">
  5. <title></title>
  6. <style>
  7. body {
  8. height: 200vh;
  9. /* 为了触发滚动事件,增加页面高度 */
  10. }
  11. </style>
  12. </head>
  13. <body>
  14. <h1>防抖和节流示例</h1>
  15. <script>
  16. // 防抖函数
  17. function debounce(func, delay) {
  18. let timer; // 定时器变量
  19. return function() {
  20. clearTimeout(timer); // 清除之前的定时器
  21. timer = setTimeout(() => {
  22. func.apply(this, arguments); // 延迟时间结束后执行函数
  23. }, delay);
  24. };
  25. }
  26. // 节流函数
  27. function throttle(func, delay) {
  28. let timer; // 定时器变量
  29. return function() {
  30. if (!timer) {
  31. timer = setTimeout(() => {
  32. func.apply(this, arguments); // 延迟时间结束后执行函数
  33. timer = null; // 清空定时器变量
  34. }, delay);
  35. }
  36. };
  37. }
  38. // 示例函数:处理滚动事件
  39. function handleScroll() {
  40. console.log("处理滚动事件");
  41. }
  42. // 使用防抖函数包装处理滚动事件的函数
  43. const debouncedHandleScroll = debounce(handleScroll, 200);
  44. // 使用节流函数包装处理滚动事件的函数
  45. const throttledHandleScroll = throttle(handleScroll, 200);
  46. // 监听滚动事件,并调用相应的处理函数
  47. window.addEventListener("scroll", debouncedHandleScroll);
  48. // 如果要使用节流函数,可以将上面一行改为下面这行
  49. // window.addEventListener("scroll", throttledHandleScroll);
  50. </script>
  51. </body>
  52. </html>

附录:

关于节流/防抖函数中 context(this) 的指向解析:

在防抖和节流函数中,this 的指向非常重要。下面分别解析一下:

防抖函数中的 this 指向

在防抖函数中,如果不加以处理,this 会指向当前调用防抖函数的对象(例如 window 对象)。因此,我们需要使用 Function.prototype.apply() 或 Function.prototype.call() 方法来明确指定 this 的值。

例如,以下代码中的 handleInput 函数在执行时,this 会指向 input 元素本身:

<input type="text" oninput="debouncedHandleInput.call(this, event)">

这里的 this 表示当前的 input 元素。通过 call() 方法将 this 明确指定为 debouncedHandleInput 函数中的 this。

节流函数中的 this 指向

在节流函数中,this 的指向与防抖函数略有不同。在节流函数中,this 通常应该指向事件的目标元素(例如 button 元素),而不是当前调用节流函数的对象(例如 window 对象)。

例如,以下代码中的 handleClick 函数在执行时,this 会指向 button 元素本身:

<button onclick="throttledHandleClick(event)">点击</button>

这里的 this 表示当前的 button 元素。在 throttledHandleClick 函数中,可以使用 this 来获取目标元素的属性、修改样式等操作。

需要注意的是,在使用箭头函数定义防抖和节流函数时,this 的指向不会改变,仍然指向外层作用域的 this。

综上所述,防抖和节流函数中的 this 指向应该根据实际情况进行明确指定。

声明:本文内容由网友自发贡献,不代表【wpsshop博客】立场,版权归原作者所有,本站不承担相应法律责任。如您发现有侵权的内容,请联系我们。转载请注明出处:https://www.wpsshop.cn/w/笔触狂放9/article/detail/716473
推荐阅读
相关标签
  

闽ICP备14008679号