00:00
我是上硅谷H5学科的熊健,在程序员节日到来之际呢,和大家分享一道面试题啊,这道题目呢在这啊,什么是函数截流,什么是函数反导,哎,这两个概念呢会比较相近,那我们呢来拆开来分析一下,首先我们来看一下什么是函数截流。那这里有句话我们来解释一下啊,就是当一个函数,当一个函数执行一次后呢,只有在大于一个设定的执行周期时啊,才会执行第二次。好一个函数执行一次后。只有。周。后才会执行第二次。好,那这个呢,可能不是那么好理解啊,那所以说咱们来再细化一下,说一下,就这时候呢,我们会遇到在开发中会遇到一个这样的问题,就是有些可能会频繁触发的网速啊。
01:11
有个需要频繁触发的函数。那么频繁触发的函数的话呢,哎,如果你触发太多的话呢,对你性能不太好,所以说处理于节约节约性能的角度上来看啊,属于。优化性能。我们会啊,去想办法只让。函数是让,就是在规定时间内。只让这个函数啊触发的第一次成像。那后面呢,不生效。说白了呢,可能我一开始要触发十次函数,我只让触发的第一次这个函数生效,而后面九次呢,它呢就不生效了。
02:04
这第一次生效,后面就逐步生效,那这种呢,我们称之为函数节流啊,那么好,那咱们来写一个解流函数,来看一看到底是怎么一回事啊,来咱们来分装一个函数。这叫做,这是一个函数。好,然后呢,这个名字呢,我们叫做。好否责一个这样的函数,那这个函数呢,你到时候调用的时候呢,我希望他来帮我做这个事,哎,你呢,就将你要写的函数给传进去,然后呢,还要给我给对我指定一个d delay规定时间啊,给我指定规定时间,好我们来写一下这个函数的意义啊,好,这个函数呢,我们称之为节流函数。这个N呢,就是要被截流的函数。那么delay的就是规定的时间,好,那参数我们搞懂了,接下来我们来写写。
03:03
那么在正常情况下呢,我们就是当我执行这个函数呢,就内部呢,将你传入的这个函数给调用一下,但是这样呢,就不能做出满足我们的需求了,我们的需求呢,只按在规定时间内呢,只按D触发的第一次生效,后面不生效。好,为了达到这个规定时间内啊,我这里面呢,就需要一些变量来去接受处理一下啊,首先我要初始化和变量,这变量呢,就都是它会记录。上一次函数触发的时间。好,我们来一个变量,叫做last time。Last time,然后呢,等于零,初始化为零都可以啊,初始化为零,那么呢,再记录一下。当前函数触发的时间。说白了就是这个当前谁去触发这个函数的时间。我们比如说一个。
04:01
它呢,等于啊,Death did not等于当前的这个时间数,等于当前时间好,那为了达到这一点呢,我们通常都是这样去说做的啊,为了让规定时间内只按出放的第一次生效的话呢,我这么做,我的time断一下啊,No time减去lasttime是否大于这个delay,你传入的这个延迟时间,如果大于的话呢,说明呢,它已经过了这个时间差了,就可以再次执行,如果没大于的话呢,我就不执行,我就啥也不做。啊,就是这里呢,来去判断,这个是让当前时间呢,减去上一次时间要大于这个延时时间。一时间好,那么这时候呢,我就会满足啊,在规定时间内呢,这个函数只会被执行一次。哎,但是如果这样写的话呢,就会出问题啊,你看这个函数呢,最终会被触发,出发的时候呢,每一次的时候都被都初始化了一个last time,那么这时候呢,它每次初始化都是零,那么它每次都是零,而你获取的long time呢,它是一个很大的值,是很大的值,所以说通常来讲,每次相减的话呢,都大于主体内侧,比如说这种写法呢,是不可取的。
05:12
那为了让这个这个能够去使用的话呢,我们会这样做啊,我们会让他return一个方式。那这里呢,我们现在是这里呢,在底层呢,去返回了一个函数,返回这个函数呢,在这里面函数里面再去获取time,诶这样做呢就能做了。哎,我们来看想一想啊,为什么这样做就能做呢?哎,其实呢,就是我这里面呢,通过B包的方式啊,在里面呢,引用的这个lasttime变量,而lasttime呢,它初始化为零,那么呢,在B包中呢,我下次我调用的是这个函数,而这个函数呢,没有去初始化拉time的值,它一直记录的是上一次的这个零的时间,所以说这样的话呢,就不会初始化这个零了,就可以做好准备点咱们这一点了。
06:01
好,那做这一点的前提是呢,你在这里面呢,还得去同步这个时间啊,同步时间在这里呢,Last time。需要等于你这个太。好,这样做的话呢,是OK的就是OK的好,我们来测试一下到底可不可取啊,我们来设定一个,比如说我给去定一个事件,叫做SC事件。绑定事件,好,当你一旦绑定这个事件的时候呢,好,那接下来指定一个回电函数,而这个回电函数呢,我就通过这个节量函数去处理所处理好传一个第一个参数呢,是一个函数,你要传递一个函数,好就传一个这样的函数,在这函数里面呢,我待会呢,就打印输出一下啊啊就是这个克事件呢被触发了。然后呢?
07:02
处罚,然后加上当前的一个时间啊,加上一个当前的时间。这样大家时间戳好,我们来研究一下可不可以,然后这里再给你一个规定时间,通常情况下呢,我们可能会规定一个200毫秒啊,你不能再出发了,好。好在测试之前呢,我们要想让系统啊滚动条,所以说在这里面呢,我们在head里面呢,写个style标签,在这里面呢,我们就将HTML和body的高度呢,调稍微高一些啊稍微高一些。我们调为500%,好,这时候呢,就会出现滚动条了,调500%,我们来测试一下啊。Avi。好,这时候呢,出现滚动条,当你的鼠标滚能往下滚的时候,诶,你会发现呢,SC事件呢,一直被触发,而我一直在滚啊,这时候你会发现每一次啊,当下次的时间减去上一次时间呢,它一定要大于这个200毫秒的时候,才可能会被触发啊,这就是咱们的解决函数,如果是正常的一个函数的话呢,在你这个时间内呢,它会被触发可能十几次之多,所以说通过节流函数呢,我们会极大的减少这个函数调用的次数,从而去节约你的性能,优化你的性能,那么这个呢,就是节流函数的一个做法啊,就是大家看一下啊,我们呢,就是通过定义个函数,记录它上一次的出发时间,然后呢返回一个新的函数,然后这里面呢,再去获取当前触发时间,然后上一次当前数据发时间减去上一次时间,但它大于你传入的这个延迟时间的话呢,才去执行这个函数,然后执行函数之后啊,你记得要同步一下上次触发的时间。
08:50
好,这样的话呢,就能做好,那这里面呢,可能涉及到一个Z指向的问题啊,因为切到多层函数啊,为了让this指向没有问题的话呢,通常我们会靠一个这次像当前这个函数的Z呢,传入到我这个FN中,那这样Z直线就没有问题了啊,修正这this指线问题。
09:13
好,就是这样的,好,这以上呢,就是我们这个节流函数的写法了啊,那大家好看一看。好,我们呢,把它收一收啊,收一收,接下来呢,我们来去研究下一个东西,下一个概念,下一个概念呢,我们称之为。反导函数或者说函数反导啊。好。反导函数是怎么一回事呢?就是一个需要频繁除法的函数。在我规定的某个时间内。啊,只让最后一次睡觉。
10:02
啊,前面的呢,不剩下。好,这个呢,就是我们的反动函数,好,那我们呢,说这么多,现在测试一下,写一个咱们的反动函数啊好来看一个,我们来写一个函数。的一个方式。好,这个方式呢,我叫做de Bo啊de bos好这里面呢,也同样呢,需要你传一个函数,以及一个延迟时间,一个延迟时间,好那在这里面呢,我们再来看看到底该怎么写。首先呢,我们为了达到这个延迟,实际上最后一次生效啊,通常情况下呢,我们就是给他设置一个延时器,通过设置延时器的方式,我们做好这点,我们可以设置。好,此帽呢,在规定延时时间内呢,我再去执行你单体函数。哎,这里面呢,我们就不改了啊,这个方式在这里面呢,去执行你这个函数,然后呢,再讲这个延迟时间呢,给它设置上去。
11:06
但这样设置的话呢,你会发现啊,它仅仅只会在延迟一段时间后呢,执行你单体这个函数。啊,为了达到让最后一次生效的特点呢,我们会这样做啊。我在这里面呢,来看一下怎么写的,一个timer复数化为那。然后呢,再加上timer呢。等于你这September啊,好September呢,就记录着我的September,这个是这个。对应的这个帽子,然后呢,一上来的时候啊,我就肯定要帽子将你这个东西呢,也清除一下。啊,注意这个很重要啊,一上来呢清除岩石气,一上来清除岩石气,那这样的话呢,就能清除什么呢,实际上清除的就是上一次的延时器,好清除上一次延时器,然后呢再去重新。
12:05
设置一个新的一示器。啊,重新设置新的延时器,然后在这新的延时置器里面呢,再去执行这个FN函数,好在这里面呢,我们目前来讲的话呢,又会出现是咱们前面那个窘境啊,就是time呢,每次都输出方为呢,它并不能记录啊,这个呢,我就是要来记录啊上一次的这个延示器。但是呢,这样的话呢,每次都初始化文档的话呢,它就压根记录不了,记录不,所以说呢,我们在这里面呢,还得一个新的方式。在这新的方式里面呢,一上来去清除一下这个time,然后再去重新设置新的延时器啊,这时候呢才靠谱啊才靠谱好,这里面呢,同样的也涉及到一个this指向的问题,所以说我们这里比如说我们换一下啊,然也能去把定这个this啊,这样的话呢,This指向呢就没问题了。
13:04
好,那这个东西到底靠不靠谱呢?我们接下来来测试一下啊,来测试一下,比方说。来我要测试的话呢,把上面这个给注释掉了,是是这样,然后呢,我们来测试啊,那这里面呢,我们去找我们去写一个HL写个按钮。在这个里面呢,我写个八三按钮。啊,这里面就是按钮,普通按钮,给他一个ID叫做飞天。好在这里面呢,我们给这BTM去绑定一个点击事件啊啊点击事件。Document。D就是这个,然后呢,把那个on click事件好,它的事件呢,这个回调函数呢,我们就用这个反导函数去处理一下。好,你要传一个函数,就是这个一个传函数在这里面打开输出一下啊,比如说是点击事件被触发了。好,这里面再加上你当前触发的这个时间。
14:03
好,接下来呢,我再要传一个延迟时间,比方说呢,延迟个一秒钟啊,延迟一秒钟,好,那我们现在来看一下,到底咱们写的能不能实现这个功能,来刷新一下页面。忘掉啊好,我们来看一下往上走啊,往上走这里有个按钮,那我们来去F2F12检查一下也行啊着这我们来刷新一下看看行不行,我点。好,你看明显呢,当我点击这个按钮的时候呢,它出现了一定的延迟才会输出,好当不断点不断点不断点你再触发多少次啊,不管你怎么点它都不会有输出的,一直到点完之后呢,过完一秒之后,才会将这个点击时间给你触发。那这样的话呢,我就能让啊用户多次操作,多次点击这个按钮的时候,他多次点击,正常来讲应该是点击一次触发一次,但是呢,现在呢,我点击一次呢,我只让最后一次触发,就通过这个可定啊戴帽子通过这个太帽子一上来呢,将上一次你点击的时候呢,给清除掉啊,重新设置一个新的延时器,这样呢就能做好咱们这个反导函数,反函数好,那以上呢,就是我们截流函数和反导函数的做法。
我来说两句