javascript中的throttle和debounce浅析


Posted in Javascript onJune 06, 2014

throttle

我们这里说的throttle就是函数节流的意思。再说的通俗一点就是函数调用的频度控制器,是连续执行时间间隔控制。主要应用的场景比如:

1.鼠标移动,mousemove 事件
2.DOM 元素动态定位,window对象的resize和scroll 事件

有人形象的把上面说的事件形象的比喻成机关枪的扫射,throttle就是机关枪的扳机,你不放扳机,它就一直扫射。我们开发时用的上面这些事件也是一样,你不松开鼠标,它的事件就一直触发。例如:

var resizeTimer=null;
$(window).on('resize',function(){
       if(resizeTimer){
           clearTimeout(resizeTimer)
       }
       resizeTimer=setTimeout(function(){
           console.log("window resize");
       },400);

debounce

debounce和throttle很像,debounce是空闲时间必须大于或等于 一定值的时候,才会执行调用方法。debounce是空闲时间的间隔控制。比如我们做autocomplete,这时需要我们很好的控制输入文字时调用方法时间间隔。一般时第一个输入的字符马上开始调用,根据一定的时间间隔重复调用执行的方法。对于变态的输入,比如按住某一个建不放的时候特别有用。

debounce主要应用的场景比如:
文本输入keydown 事件,keyup 事件,例如做autocomplete

这类网上的方法有很多,比如Underscore.js就对throttle和debounce进行封装。jQuery也有一个throttle和debounce的插件:jQuery throttle / debounce,所有的原理时一样的,实现的也是同样的功能。再奉上一个自己一直再用的throttle和debounce控制函数:

/*
* 频率控制 返回函数连续调用时,fn 执行频率限定为每多少时间执行一次
* @param fn {function}  需要调用的函数
* @param delay  {number}    延迟时间,单位毫秒
* @param immediate  {bool} 给 immediate参数传递false 绑定的函数先执行,而不是delay后后执行。
* @return {function}实际调用函数
*/
var throttle = function (fn,delay, immediate, debounce) {
   var curr = +new Date(),//当前事件
       last_call = 0,
       last_exec = 0,
       timer = null,
       diff, //时间差
       context,//上下文
       args,
       exec = function () {
           last_exec = curr;
           fn.apply(context, args);
       };
   return function () {
       curr= +new Date();
       context = this,
       args = arguments,
       diff = curr - (debounce ? last_call : last_exec) - delay;
       clearTimeout(timer);
       if (debounce) {
           if (immediate) {
               timer = setTimeout(exec, delay);
           } else if (diff >= 0) {
               exec();
           }
       } else {
           if (diff >= 0) {
               exec();
           } else if (immediate) {
               timer = setTimeout(exec, -diff);
           }
       }
       last_call = curr;
   }
};/*
* 空闲控制 返回函数连续调用时,空闲时间必须大于或等于 delay,fn 才会执行
* @param fn {function}  要调用的函数
* @param delay   {number}    空闲时间
* @param immediate  {bool} 给 immediate参数传递false 绑定的函数先执行,而不是delay后后执行。
* @return {function}实际调用函数
*/
var debounce = function (fn, delay, immediate) {
   return throttle(fn, delay, immediate, true);
Javascript 相关文章推荐
jQuery学习笔记之jQuery.extend(),jQuery.fn.extend()分析
Jun 09 Javascript
13 款最热门的 jQuery 图像 360 度旋转插件推荐
Dec 09 Javascript
检测一个函数是否是JavaScript原生函数的小技巧
Mar 13 Javascript
Jquery遍历Json数据的方法
Apr 20 Javascript
Javascript递归打印Document层次关系实例分析
May 15 Javascript
JavaScript调用浏览器打印功能实例分析
Jul 17 Javascript
AngularJS基础 ng-disabled 指令详解及简单示例
Aug 01 Javascript
jQuery css() 方法动态修改CSS属性
Sep 25 Javascript
JS表单提交验证、input(type=number) 去三角 刷新验证码
Jun 21 Javascript
JavaScript查看代码运行效率console.time()与console.timeEnd()用法
Jan 18 Javascript
详解React 元素渲染
Jul 07 Javascript
使用Canvas绘制一个游戏人物属性图
Mar 25 Javascript
单击某一段文字改写文本颜色
Jun 06 #Javascript
Javascript中的异步编程规范Promises/A详细介绍
Jun 06 #Javascript
AMD异步模块定义介绍和Require.js中使用jQuery及jQuery插件的方法
Jun 06 #Javascript
jQuery插件开发详细教程
Jun 06 #Javascript
手写的一个兼容各种浏览器的javascript getStyle函数(获取元素的样式)
Jun 06 #Javascript
jquery进行数组遍历如何跳出当前的each循环
Jun 05 #Javascript
js检验密码强度(低中高)附图
Jun 05 #Javascript
You might like
PHP数组与对象之间使用递归实现转换的方法
2015/06/24 PHP
PHP随手笔记整理之PHP脚本和JAVA连接mysql数据库
2015/11/25 PHP
PHP简单创建压缩图的方法
2016/08/24 PHP
getElementById在任意一款浏览器中都可以用吗的疑问回复
2007/05/13 Javascript
js禁止小键盘输入数字功能代码
2011/08/01 Javascript
javascript表单验证大全
2015/08/12 Javascript
JS实现带鼠标效果的头像及文章列表代码
2015/09/27 Javascript
javascript生成img标签的3种实现方法(对象、方法、html)
2015/12/25 Javascript
Eclipse编辑jsp、js文件时卡死现象的解决办法汇总
2016/02/02 Javascript
javascript实现起伏的水波背景效果
2016/05/16 Javascript
Jquery实现跨域异步上传文件总结
2017/02/03 Javascript
jquery.picsign图片标注组件实例详解
2018/02/02 jQuery
微信小程序Echarts覆盖正常组件问题解决
2019/07/13 Javascript
JavaScript 中的六种循环方法
2021/01/06 Javascript
如何管理Vue中的缓存页面
2021/02/06 Vue.js
总结网络IO模型与select模型的Python实例讲解
2016/06/27 Python
Python实现图片转字符画的示例
2017/08/22 Python
解决phantomjs截图失败,phantom.exit位置的问题
2018/05/17 Python
python使用suds调用webservice接口的方法
2019/01/03 Python
mac系统下Redis安装和使用步骤详解
2019/07/09 Python
快速解决vue.js 模板和jinja 模板冲突的问题
2019/07/26 Python
Python实现PyPDF2处理PDF文件的方法示例
2019/09/25 Python
TensorFlow——Checkpoint为模型添加检查点的实例
2020/01/21 Python
浅谈python opencv对图像颜色通道进行加减操作溢出
2020/06/03 Python
python函数超时自动退出的实操方法
2020/12/28 Python
Myprotein瑞典官方网站:畅销欧洲英国运动营养品牌
2018/01/22 全球购物
写一个方法1000的阶乘
2012/11/21 面试题
培训研修方案
2014/06/06 职场文书
北京申奥口号
2014/06/19 职场文书
坚守艰苦奋斗精神坚决反对享乐主义整改措施
2014/09/17 职场文书
机动车登记业务委托书
2014/10/08 职场文书
2014光棍节大学生联谊活动方案
2014/10/10 职场文书
亚布力滑雪场导游词
2015/02/09 职场文书
PyTorch dropout设置训练和测试模式的实现
2021/05/27 Python
pandas求平均数和中位数的方法实例
2021/08/04 Python
Redis集群新增、删除节点以及动态增加内存的方法
2021/09/04 Redis