自我介绍:大家好,我是吉帅振的网络日志;微信公众号:吉帅振的网络日志;前端开发工程师,工作4年,去过上海、北京,经历创业公司,进过大厂,现在郑州敲代码。
JS函数专栏
一、防抖debounce函数
1.定义
n秒后执行,事件触发后延迟执行,输入期间不执行触发操作。无操作及延迟时间过后触发,一般适用于频繁触发的操作。
2.应用场景
输入框中频繁的输入内容,搜索或者提交信息;频繁的点击按钮,触发某个事件;监听浏览器滚动事件,完成某些特定操作;用户缩放浏览器的resize事件。
3.基本实现
- //原理是用setTimeout函数达到延迟效果,连续操作时使用clearTimeout函数不断清除定时器,重置延迟时间,阻止连续触发。
- let inp = document.getElementById("inp")
- var timeout;
- inp.oninput = function () {
- clearTimeout(timeout)
- timeout = setTimeout(() => {
- console.log(this.value)
- },1000)
- }
-
- //优化:参数和this指向;增加取消功能;第一次立即执行;返回值
- function debounce(fn,delay,immediate=false,resultCallback){
- let timer=null
- // console.log(this)//window
- // 定义控制立即执行的变量,false表示没有执行过
- let isInvoke=false
- // 真正的处理函数
- function _debounce(...args){
- // 取消事件执行操作
- if(timer) clearTimeout(timer)
- // console.log(this)//element元素
- if(immediate&&!isInvoke){
- const result=fn.apply(this,args)
- resultCallback(result)
- isInvoke=true
- }else{
- // 延迟执行
- timer=setTimeout(()=>{
- const result=fn.apply(this,args)
- resultCallback(result)
- timer=null
- isInvoke=false
- },delay)
- }
- }
- // 封装取消请求
- _debounce.cancel=function(){
- if(timer) clearTimeout(timer)
- timer=null
- isInvoke=false
- }
- return _debounce
- }
二、节流throttle函数
1.定义
n秒内只执行一次,节流函数是规定一段时间内无法触发,时间过了才触发,即使不断输入值,但只要1秒钟过了,也会触发。
2.应用场景
监听页面的滚动事件;鼠标移动事件;用户频繁点击按钮操作;游戏中的一些设计。
3.基本实现
- //节流,就是节制的意思,能省就省。写法与防抖函数类似,都是使用定时器,不过它们还是有差别的。
- let inp = document.getElementById("inp")
- var timeout
- let flag = true
- inp.oninput = function () {
- if (!flag) {
- return
- }
- flag = false
- timeout = setTimeout(() => {
- console.log(123)
- flag = true
- }, 1000)
- }
-
- //优化:节流最后一次也可以执行;增加取消功能;返回值
- function throttle(fn,interval,options={leading:true,trailing:false}){
- let lastTime=0
- const {leading,trailing,resultCallback}=options
- let timer=null
- function _throttle(...args){
- const nowTime=new Date().getTime()
- // leading优化
- if(!leading&&!lastTime) lastTime=nowTime
- let remainTime=interval-(nowTime-lastTime)
- if(remainTime<=0){
- if(timer){
- clearTimeout(timer)
- timer=null
- }
- // 参数优化
- const result=fn.apply(this,args)
- if(resultCallback) resultCallback(result)
- lastTime=nowTime
- return
- }
- // 优化trailing
- if(!timer&&trailing){
- timer=setTimeout(()=>{
- // 参数优化
- const result=fn.apply(this,args)
- if(resultCallback) resultCallback(result)
- timer=null
- lastTime=!leading?0:new Date().getTime()
- },remainTime)
- }
- }
- _throttle.cancel=function(){
- if(timer) clearTimeout(timer)
- timer = null
- lastTime = 0
- }
- return _throttle
- }