所以我只是想在underscore.js中了解节流代码。
_.throttle = function(func, wait, options) {
var context, args, result;
var timeout = null;
var previous = 0;
options || (options = {});
var later = function() {
previous = options.leading === false ? 0 : _.now();
timeout = null;
result = func.apply(context, args);
context = args = null;
};
return function() {
var now = _.now();
if (!previous && options.leading === false) previous = now;
var remaining = wait - (now - previous);
context = this;
args = arguments;
if (remaining <= 0) {
clearTimeout(timeout);
timeout = null;
previous = now;
result = func.apply(context, args);
context = args = null;
} else if (!timeout && options.trailing !== false) {
timeout = setTimeout(later, remaining);
}
return result;
};
};
我想知道为什么context,args和timeout被设置为null。我原本以为他们是为了帮助垃圾收集而设置的。为了测试我创建了一个大字符串,将其传递给一个函数并限制该函数。我使用Chrome开发工具拍摄了两个快照 - 第一个使用将三个变量设置为null的行注释掉,另一个用未注释掉的行。
var dummyFunc1 = function(testStr) {
console.log("HELLO");
};
var dummyFunc2 = function(testStr) {
console.log("BOOM");
}
var dummyFunc3 = function(testStr) {
console.log("STOOP");
}
var testStr = '';
for (var i = 0; i < 1000000; i++){
testStr += i;
}
var largeThrottled1 = _.throttle(dummyFunc1, 1000);
var largeThrottled2 = _.throttle(dummyFunc2, 1000);
var largeThrottled3 = _.throttle(dummyFunc3,1000);
largeThrottled1(testStr);
largeThrottled1(testStr);
然而,似乎并没有太大区别。
那么为什么那些线呢?
答案 0 :(得分:1)
我认为它与预防内存泄漏有关,正如您已经想到的那样
让我们假设您创建了大量的限制函数,用大量数据调用它们然后再也不调用它们。然后由_.throttle
创建的函数仍将在闭包范围内保持对该数据的引用。它们在理论上仍然可以通过返回的函数到达,因此只要您不处理受限制的函数,GC就无法清理该数据。因此,将这些变量设置为null可确保不再使用任何不再使用的引用,从而防止内存泄漏。