简而言之,垃圾收集是 Javascript 解释器/虚拟机的后台进程,它自动释放程序不再需要的对象的内存。
例如,既然您将其视为事件侦听器:当您从某个事件调度程序中删除事件侦听器(通常是一个函数)时,程序的其他部分很可能不会引用该事件侦听器。因此,垃圾收集器可以并且将会(在某个未知的时间)释放事件侦听器占用的内存。
由于闭包引用了作用域对象,因此为了对闭包进行垃圾收集,它不仅需要被取消引用,而且还需要被取消引用。
如果我修改一下你的例子:
/* some stuff ... */
function add10(a) {
var adder = function (x) {
return function(y) {
return x + y;
}
}
var sum = adder(10); //creates a closure
return sum(a);
}
var thirty = add10(20);
/* Some more stuff ... */
After add10
被调用时,即使程序继续执行更多的东西,垃圾收集器也可以释放与闭包相关的内存sum
,因为不再被引用,nor是与其关联的范围。
而在这个例子中:
/* some stuff ... */
function add10AndGet20Adder(a) {
var adders = function (x, y) {
return [function(z) {
return x + z;
}, function(z) {
return y + z;
}]
}
var sums = adders(10, 20); //creates a closure
return [sums[0](a), sums[1]];
}
var result = add10AndGet20Adder(50);
var sixty = result[0];
var add20 = result[1];
/* Some more stuff ... */
当执行更多的事情时,sums[0]
不再引用,BUT add20
(sums[1]
) 仍然具有对引用范围的引用x
andy
,因此两个闭包都没有sums
可以被垃圾收集器释放,直到add20
被程序引用。
我希望这能让它更清楚,尽管这些示例当然与真实代码相差甚远。实际上,只有当您开发一个长期使用闭包的程序(例如单页应用程序或nodeJS服务器)时,您才需要担心这一点。否则,闭包的内存使用不太可能成为问题。
这个问题提供了有关 Javascript 垃圾收集的更多详细信息:什么是 JavaScript 垃圾回收? https://stackoverflow.com/questions/864516/what-is-javascript-garbage-collection