2

函数防抖

场景

假设网站有个搜索框, 用户输入文本我们会自动联想匹配出一些结果供用户选择,我们可能首先想到的做法就是监听keypress事件, 然后异步查询结果. 但是如果用户快速的输入了一串字符, 假设是10个字符, 那么就会在瞬间触发10次请求, 这无疑不是我们想要的, 我们想要的是用户停止输入的时候才去触发查询的请求.

原理

函数防抖就是让某个函数在上一次执行后, 满足等待某个时间内不再触发此函数后再执行, 而在这个等待时间内再次触发此函数, 等待时间会重新计算.

实现

underscore.js的函数防抖定义: _.debounce(fn, wait, [immediate]);

debounce接收三个参数:
@params fn: 需要进行函数防抖的函数;
@params wait: 需要等待的时间, 单位为毫秒;
@params immediate: 如果为true, 则debounce会在调用时立刻执行一次fn,
                   而不需要等到wait结束后.

_.debounce = function(fn, wait, immediate) {
    var timeout,
        args,
        context,
        timestamp,
        result;

    var later = function() {
        var last = _.now() - timestamp;

        if(last < wait && last >= 0) {
            timeout = setTimeout(later, wait - last);
        } else {
            timeout = null;
            if(!immediate) {
                result = fn.apply(context, args);

                if(!timeout) {
                    context = args = null;
                }
            }
        }
    };

    return function() {
        context = this;
        args = arguments;
        timestamp = _.now();
        var callNow = immediate && !timeout;

        if(!timeout) {
            timeout = setTimeout(later, wait);
        }

        if(callNow) {
            result = fn.apply(context, args);
            context = args = null;
        }

        return result;
    }
};

// demo:
$('#input').keypress(_.debounce(function() {
    //异步调用查询
}, 300));

引路人
146 声望12 粉丝