ZetCode

JavaScript let 关键字

最后修改于 2025 年 4 月 16 日

在本文中,我们将探讨 JavaScript 中的 let 关键字,它声明块级作用域变量。我们将研究它的行为和优势。

let 关键字

let 关键字声明的变量仅限于它们使用的块、语句或表达式。与 var 不同,let 变量不会被提升到其作用域的顶部。这可以防止 JavaScript 中常见的范围界定问题。

使用 let 声明的变量具有块级作用域,这意味着它们仅存在于最近的 curly braces 内。它们不能在同一作用域中重新声明,但可以被重新赋值。这使得代码更可预测且更易于维护。

临时死区是指变量存在但无法访问的时期。它从块的开始开始,到声明被处理时结束。这可以防止在声明之前引用变量。

基本 let 声明

此示例显示了 let 关键字的基本用法。

main.js
let message = "Hello, World!";
console.log(message);

message = "Updated message";
console.log(message);

在这里,我们使用 let 声明一个变量 message 并对其进行初始化。然后,我们为其重新赋值一个新值。与 const 不同,let 允许重新赋值。该变量被块级作用域限定到当前的执行上下文。

$ node main.js
Hello, World!
Updated message

块级作用域演示

此示例演示了 let 的块级作用域行为。

main.js
let x = 10;

if (true) {
    let x = 20;
    console.log(x); // 20
}

console.log(x); // 10

if 块内的 x 变量是一个与外部 x 不同的变量。这显示了 let 如何在每个块作用域中创建新变量。外部 x 保持不变。

$ node main.js
20
10

临时死区

此示例说明了 let 的临时死区行为。

main.js
console.log(y); // ReferenceError
let y = 5;

尝试在声明之前访问 y 会抛出 ReferenceError。这与 var 不同,后者会返回 undefined。临时死区阻止在声明之前使用。

$ node main.js
ReferenceError: Cannot access 'y' before initialization

使用 let 的循环计数器

在循环计数器中使用 let 会为每次迭代创建一个新的绑定。

main.js
for (let i = 0; i < 3; i++) {
    setTimeout(() => {
        console.log(i);
    }, 100);
}

每次迭代都有自己的 i 变量,解决了循环中经典的闭包问题。使用 var,所有超时都会记录 3。在这里,我们按预期得到 0、1、2,这归功于块级作用域。

$ node main.js
0
1
2

防止重新声明

let 阻止在同一作用域中重新声明同一变量。

main.js
let name = "Alice";
let name = "Bob"; // SyntaxError

尝试在同一作用域中重新声明 name 会抛出 SyntaxError。这有助于捕获可能意外重用变量的潜在错误。但是,不同的作用域可以具有同名的变量。

$ node main.js
SyntaxError: Identifier 'name' has already been declared

switch 语句中的块级作用域

当使用 let 时,switch 语句为每个 case 创建单独的块作用域。

main.js
let choice = 1;

switch (choice) {
    case 1:
        let message = "First case";
        console.log(message);
        break;
    case 2:
        let message = "Second case"; // SyntaxError
        console.log(message);
        break;
}

这失败了,因为 message 正在同一块中被重新声明。要修复此问题,请将每个 case 包装在 curly braces 中以创建单独的块。这演示了 switch 语句如何共享同一块作用域。

$ node main.js
SyntaxError: Identifier 'message' has already been declared

实际用例:块级作用域变量

这是一个实际的例子,展示了 let 如何提高代码安全性。

main.js
function calculate() {
    let result = 0;
    
    for (let i = 0; i < 5; i++) {
        result += i;
    }
    
    // i is not accessible here
    console.log(result);
    
    if (result > 3) {
        let message = "Large result";
        console.log(message);
    }
    
    // message is not accessible here
}

calculate();

这显示了 let 如何将变量限制在其逻辑块中。循环计数器 imessage 变量只能在其各自的块中访问。这可以防止意外误用。

$ node main.js
10
Large result

来源

let - 语言参考

在本文中,我们演示了如何使用 let 关键字在 JavaScript 中声明块级作用域变量。

作者

我叫 Jan Bodnar,是一位充满激情的程序员,拥有丰富的编程经验。自 2007 年以来,我一直在撰写编程文章。迄今为止,我撰写了 1,400 多篇文章和 8 本电子书。我拥有超过十年的编程教学经验。

查看 所有 JavaScript 教程。