防抖、节流、闭包介绍

225 阅读5分钟

防抖

1.防抖的概念 什么是防抖?

防抖指的就是触发事件之后,不管触发多少次,在n秒之后只执行一次,如果在n秒后内又触发了事件,则会重新计算执行时间

2.防抖的实现

语法:函数_.debounce(func,[wait=0],[options])

三个参数:第一个参数为需要防抖的函数,第二个参数是需要延迟的毫秒数,第三个参数是选项对象

返回的是新的防抖函数

3.官网

www.lodashjs.com/docs/lodash…

4.使用场景

input输入框,连续输入的时候,只要输入的间隔不超过设置的时间间隔,那么这个事件只会执行一次,也就是末尾那一次

点击事件,防止用户多次点击

5.防抖的实现原理&手写防抖

// API式
inp.oninput = _.debounce(changeInput, 1000) // 防抖

// 手写防抖
let count = 0; // 计算执行的次数
// 触发的函数
function changeInput(e) { // e就是事件对象
    console.log('触发了', count++, '次', this, e);
}

// 写一个防抖函数==>高阶函数
function debounce(fn, delay) {
    let timer = null; // debounce只触发一次
    return function (...args) { // 真正的事件处理程序
        if (timer) { // 清除掉计时器 重新机试
            clearTimeout(timer)
        }
        timer = setTimeout(() => {
            fn.apply(this, args) // 独立调用 this指向widnow 需要改变this指向
        }, delay)
    }
}
inp.oninput = debounce(changeInput, 1000)

节流

1.节流的概念 什么是节流

所谓节流,就是事件一直被触发的话,第一次触发立即执行。接下来每隔一段时间才会触发一次,也就是来减少调用频率,从而提高性能

2.节流的实现

语法:函数_.throttle(func,[wait=0],[options])

三个参数:第一个参数为需要节流的函数,第二个参数是需要节流的毫秒数,第三个参数是选项对象

返回的是节流函数

3.官网

www.lodashjs.com/docs/lodash…

4.使用场景

在滚动事件或者窗口resize事件时需要做一个复杂的计算,如果不限制函数的调用频率,会加重浏览器负担,造成性能浪费

5.节流的实现原理&手写节流

// API式
inp.oninput = _.throttle(changeInput, 2000) // 节流

let count = 0; // 计算执行的次数
// 触发的函数
function changeInput(e) { // e就是事件对象
    console.log('触发了', count++, '次', this, e);
}

// 写一个节流函数
function throttle(fn, delay) {
    let starttime = Date().now(); // 获取当前时间戳
    return function (...args) {
        let newtime = Date().now(); // 调用是再获取新的时间戳
        if (newtime - starttime >= delay) {
            fn.apply(this, args);
            starttime = newtime; // 更新开始时间戳
        }
    }
}
inp.oninput = throttle(changeInput, 2000)

闭包

1.什么是闭包

函数及函数周围的自由变量会形成一个闭包

2.闭包的特性

1.函数里面套函数

2.可以让你在一个内层函数中访问到其他外层函数的作用域

3.参数和变量不会被垃圾回收机制回收

3.闭包的使用场景

最常见的就是防抖、节流 同上

4.闭包的优、缺点

优点:保护函数内的变量安全、在内存中保持一个变量、匿名自执行函数可以减少内存消耗

缺点:可能会造成内存泄漏

扩展

1.内存泄漏

内存泄漏是指程序在运行过程中分配的内存空间没有被正确释放,导致这些内存空间无法被再次使用,最终导致程序运行变慢或崩溃。内存泄漏通常是由于程序中存在未释放的动态分配内存的指针或对象,或者是由于程序中存在循环引用的对象,导致这些对象无法被垃圾回收器正确回收。

为了避免内存泄漏,需要注意以下几点:

  1. 在使用动态分配内存时,一定要记得在不需要使用这些内存时及时释放。
  2. 避免循环引用的情况出现,可以使用智能指针等工具来管理内存。
  3. 在编写代码时,要注意内存的使用情况,避免出现内存泄漏的情况。
  4. 在程序运行过程中,可以使用内存检测工具来检测内存泄漏的情况,及时发现并解决问题。

2.js执行机制

JavaScript 执行机制主要包括以下几个方面:

  1. 解析:JavaScript 引擎首先会对代码进行解析,将代码转换成抽象语法树(AST)。
  2. 预编译:在代码执行前,JavaScript 引擎会对代码进行预编译,包括变量提升、函数声明提升等操作。
  3. 执行:JavaScript 引擎按照代码的顺序执行,遇到函数调用时,会将函数压入调用栈中,等待执行完毕后再弹出。
  4. 作用域:JavaScript 采用词法作用域,即变量的作用域由代码的位置决定,与函数的调用顺序无关。
  5. 异步:JavaScript 支持异步编程,通过回调函数、Promise、async/await 等方式实现。

总的来说,JavaScript 执行机制是单线程的,采用事件循环机制实现异步编程,通过回调函数等方式实现非阻塞式的代码执行。

3.垃圾回收机制

垃圾回收机制是指一种自动化的内存管理机制,用于管理计算机程序运行时所使用的内存。在程序运行时,内存中会产生大量的对象,如果这些对象不再被程序使用,但仍然占用内存,就会导致内存泄漏,从而影响程序的性能和稳定性。垃圾回收机制通过自动检测和回收不再使用的对象,释放内存空间,从而避免内存泄漏的问题。

垃圾回收机制的实现方式有多种,其中最常见的是基于引用计数和基于标记-清除的算法。引用计数是指在每个对象中记录该对象被引用的次数,当引用次数为0时,该对象就可以被回收。标记-清除算法则是通过标记所有活动对象,然后清除所有未标记的对象来回收内存。

垃圾回收机制是现代编程语言中的一项重要特性,例如Java、Python、JavaScript等语言都具有垃圾回收机制。它可以减轻程序员的内存管理负担,提高程序的可靠性和稳定性。