以下 Javascript 程序:
function f() {
function g() { console.log(x); }
let x = 0;
g(); // prints 0
x = 1;
g(); // prints 1
return g;
}
let g = f();
g(); // prints 1
输出:
0
1
1
所以似乎首先通过引用g
捕获(因为 inside ,然后打印然后何时反弹),这意味着闭包环境看起来像,然后通过值(因为 outside ,在body末尾脱离上下文时打印) ,这意味着闭包环境看起来像.x
f
g()
0
1
x
g
{'x': x}
f
g()
1
x
f
g
{'x': 1}
我试图将此行为与提供按引用和按值捕获的 C++ lambda 相关联,但与 Javascript 相反,不允许按引用捕获通过变成按值捕获(而是调用lambda 成为未定义的行为)。
这是对 Javascript 捕获的正确解释吗?
如果这种解释是正确的,那将清楚地解释块范围变量 ( let
) 的捕获如何在for
循环中工作:
let l = [];
for (let x = 0; x < 3; ++x) {
l.push(function () { console.log(x); });
}
l[0](); // prints 0
l[1](); // prints 1
l[2](); // prints 2