为什么 'error' 变量重新分配的功能范围不在 catch{} 块内?
Why isn't 'error' variable reassignment functionally scoped inside of catch{} block?
我正在 JavaScript 中使用 try-catch 块,并且 运行 有一些我不完全理解的变量作用域行为。
我知道 console.log(boo)
将 20
打印到控制台,因为该变量已使用 var
关键字声明,因此它在功能范围内(即不是块范围到 catch块)。
但是,我不明白为什么 err
变量没有像 boo
变量一样限定在 IIFE 中。因此我不明白为什么它在 catch 块之外 undefined
。
(function() {
try {
throw new Error();
} catch (err) {
var err = 10;
var boo = 20;
console.log(err); //'10' (as I expect)
}
// Why doesn’t this log '10' ???
console.log(err); // 'undefined' (but I expected '10')
console.log(boo); // '20' (as I expect)
})();
我找到了答案。
是因为异常'identifier'(即上例中的'err'变量)在catch块执行完毕后不可用。这似乎是在 JS 中处理作用域的一种特殊情况,在进行一些挖掘之前绝对是 'gotcha'。
希望这对其他人有帮助!
来自docs:
虽然 var
将符号提升到功能块的顶部,但 catch 子句的 "argument" 是该子句的局部。由于您已将提升值命名为与子句符号相同的名称,因此这可能会造成混淆。本质上,您的代码与:
(function () {
var err;
var boo;
try {
throw new Error();
} catch (err) {
err = 10; // Set the catch's "local" `err` identifier to `10`
boo = 20; // Set the hoisted `boo` identifier to `20`
console.log(err);
}
console.log(err); // The hoisted `err` was never set.
console.log(boo); // ’20’ (as I expect)
})();
您可能还会将 catch 子句中的 err
视为 function/clause 的参数;它的作用域是函数的局部作用域,与全局作用域无关(无论该符号是否存在于全局作用域中)。
我正在 JavaScript 中使用 try-catch 块,并且 运行 有一些我不完全理解的变量作用域行为。
我知道 console.log(boo)
将 20
打印到控制台,因为该变量已使用 var
关键字声明,因此它在功能范围内(即不是块范围到 catch块)。
但是,我不明白为什么 err
变量没有像 boo
变量一样限定在 IIFE 中。因此我不明白为什么它在 catch 块之外 undefined
。
(function() {
try {
throw new Error();
} catch (err) {
var err = 10;
var boo = 20;
console.log(err); //'10' (as I expect)
}
// Why doesn’t this log '10' ???
console.log(err); // 'undefined' (but I expected '10')
console.log(boo); // '20' (as I expect)
})();
我找到了答案。
是因为异常'identifier'(即上例中的'err'变量)在catch块执行完毕后不可用。这似乎是在 JS 中处理作用域的一种特殊情况,在进行一些挖掘之前绝对是 'gotcha'。
希望这对其他人有帮助!
来自docs:
虽然 var
将符号提升到功能块的顶部,但 catch 子句的 "argument" 是该子句的局部。由于您已将提升值命名为与子句符号相同的名称,因此这可能会造成混淆。本质上,您的代码与:
(function () {
var err;
var boo;
try {
throw new Error();
} catch (err) {
err = 10; // Set the catch's "local" `err` identifier to `10`
boo = 20; // Set the hoisted `boo` identifier to `20`
console.log(err);
}
console.log(err); // The hoisted `err` was never set.
console.log(boo); // ’20’ (as I expect)
})();
您可能还会将 catch 子句中的 err
视为 function/clause 的参数;它的作用域是函数的局部作用域,与全局作用域无关(无论该符号是否存在于全局作用域中)。