' let'有什么区别?和' const' ECMAScript 2015(ES6)?

时间:2014-03-10 18:14:37

标签: javascript ecmascript-5 ecmascript-6

我想知道 ES6 letconst之间的区别。它们都是块作用域,如以下代码中的示例所示:

const PI = 3.14;
console.log(PI);

PI = 3;
console.log(PI);

const PI = 4;
console.log(PI);

var PI = 5;
console.log(PI);

在ES5中,输出将为:

3.14
3.14
3.14
3.14

但在ES6中它将是:

3.14
3
4
5

我想知道为什么 ES6 允许更改const值,问题是为什么我们现在应该使用'const'?我们可以使用'let'代替吗?

注意jsbin可用于测试,选择 JavaScript 运行 ES5 代码和 Traceur 使用 ES6 功能运行它。

10 个答案:

答案 0 :(得分:55)

letconst之间的区别在于,一旦使用const将值/对象绑定到变​​量,就无法重新分配给该变量。例如:

const something = {};
something = 10; // Error.

let somethingElse = {};
somethingElse = 1000; // This is fine.

请注意,const不会使某些内容不可变。

const myArr = [];
myArr.push(10); // Works fine.

目前使对象(浅)不可变的最佳方法是在其上使用Object.freeze()

答案 1 :(得分:23)

您所看到的只是一个实施错误。根据{{​​3}},const是:

  

初始化一次,只读其后的绑定表单是有用的,并且具有   现有实现中的先例,以const的形式   声明。

它意味着只读,就像现在一样。 Traceur和Continuum中const的ES6实现是错误的(它们可能只是忽略了它)

这是ES6 spec wiki on const

答案 2 :(得分:6)

  • 在编程中使用块范围。
  • 对于每个块,让我们创建自己的新范围,您无法在该区域外访问。
  • 可以根据需要多次更改值。
  • 让绝大多数代码都非常有用。它可以极大地提高代码的可读性并减少编程错误的可能性。

        {% if post.media %}
        <img src="{{ post.image.url }}" class="img-responsive" />
        {% endif %}
    

常量

  • 它允许您使用变量进行不可变。
  • const是可读性和可维护性的良好实践,并避免使用魔法文字,例如

    let abc = 0;
    
    if(true)
     abc = 5 //fine
    
    if(true){
      let def = 5
    }
    console.log(def)
    
  • const声明必须初始化

    // Low readability
    if (x > 10) {
    }
    
    //Better!
    const maxRows = 10;
    if (x > maxRows) {
     }
    
  
      
  • const是块范围,就像我们在let:+
  • 中看到的那样   
 const foo; // ERROR: const declarations must be initialized

答案 3 :(得分:2)

摘要:

关键字letconst都是声明 block作用域变量的方法。不过有一个很大的区别:

  • let声明的变量可以重新分配。
  • const声明的变量必须在声明时初始化,并且不能重新分配。

如果尝试使用const关键字声明的变量重新分配变量,则会出现以下错误(chrome devtools):

const reassignment error

为什么要使用它?

如果我们知道一次要分配一个变量,而又不想重新分配该变量,则使用const关键字具有以下优点:

  • 我们在代码中传达了我们不想重新分配变量的信息。这样,如果其他编程人员查看您的代码(或者甚至您查看了前一段时间编写的自己的代码),您就会知道不应重新分配用const声明的变量。这样,我们的代码将变得更具说明性,并且更易于使用。
  • 我们强制采用无法重新分配变量的原则(JS引擎引发错误)。这样,如果您不小心尝试重新分配了一个不打算重新分配的变量,则可以在较早的阶段检测到该变量(因为它已记录到控制台)。

注意事项:

尽管不能重新分配用const声明的变量,但这并不意味着分配的对象是不可变的。例如:

const obj = {prop1: 1}

// we can still mutate the object assigned to the 
// variable declared with the const keyword
obj.prop1 = 10;
obj.prop2 = 2;

console.log(obj);

如果您还希望对象不可变,则可以使用Object.freeze()来实现。

答案 4 :(得分:1)

let and const

letconst声明的变量消除了特定的起吊问题,因为它们的作用域是块而不是函数。

如果在代码块中使用letconst声明了变量(用花括号{}表示),则该变量将停留在所谓的时间死区中,直到变量的声明被处理。此行为可防止仅在声明变量之后才访问变量。

使用let和const的规则

letconst还具有其他一些有趣的属性。

  • let声明的变量可以重新分配,但不能重新分配 在相同范围内重新声明。
  • const声明的变量必须分配一个初始值,但是 不能在同一范围内重新声明,也不能重新分配。

用例

最大的问题是您何时应该使用letconst?一般经验法则如下:

  • 计划将新值重新分配给变量时,请使用let,并且
  • 当您不打算将新值重新分配给广告系列时,请使用const 变量。

由于const是声明变量的最严格方法,因此建议您始终使用const声明变量,因为这样会使代码更容易推理,因为您知道标识符将不会在您程序的整个生命周期内都不得更改。如果发现需要更新或更改变量,请返回并将其从const切换到let

答案 5 :(得分:1)

/*
// declaration of const in same block scope is not allowed
const a = 10;
const a = 15; //Redeclaration of const a Error
console.log(`const outer value `+a);
*/

/*
//declaration of const in different block scope is allowed
const a = 10;
console.log(`outer value of a `+a)
{
    const a = 15; //Redeclaration of const allowed in different block scope
    console.log(`ineer value of a `+a);
}
*/

/*
// re assigning const variable in any block scope is not allowed
const a = 10;
a = 15; //invalid assignment to const 'a'
{
    a = 15;  //invalid assignment to const 'a'
}
*/

/*
// let also can not be re declared in the same block scope
let a = 10;
let a = 15; //SyntaxError: redeclaration of let a
*/

/*
// let can be redeclared in different block scope
let a = 10;
{
    let a = 15; //allowed.
}
*/

/*
// let can be re assigned in same block or different block
let a = 10;
a = 15; //allowed for let but for const its not allowed.
*/

/*
let a = 10;
{
    a = 15; //allowed
}
*/

答案 6 :(得分:0)

以下是我做过的一些笔记,对我在这个问题上有帮助。还将constletvar进行比较。

关于var

// Var
// 1. var is hoisted to the top of the function, regardless of block
// 2. var can be defined as last line and will be hoisted to top of code block
// 3. for undefined var //output error is 'undefined' and code continues executing
// 4. trying to execute function with undefined variable
// Example: // log(myName); // output: ReferenceError: myName is not defined and code stops executing 

关于letconst

// Let and Const
// 1. use `const` to declare variables which won't change
// 2. `const` is used to initialize-once, read-only thereafter
// 3. use `let` to declare variables which will change
// 4. `let` or `const` are scoped to the "block", not the function
// 5. trying to change value of const and then console.logging result will give error
// const ANSWER = 42;
// ANSWER = 3.14159;
// console.log(ANSWER);
// Error statement will be "TypeError: Assignment to constant variable." and code will stop executing
// 6. `let` won't allow reference before definition
// function letTest2 () {
//   log(b);
//   let b = 3;}
// Error statement will be "ReferenceError: b is not defined." and code will stop executing

答案 7 :(得分:0)

ES6 let和const

新的let允许您声明一个范围仅限于块的变量(局部变量)。主要区别在于var变量的范围是整个封闭函数:

if (true) {
  var foo = 42; // scope globally
}

console.log(foo); // 42

在范围内使用let

if (true) {
  let foo = 42; // scoped in block
}

console.log(foo); // ReferenceError: bar is not defined

在函数范围内使用var与使用let相同:

function bar() {
  var foo = 42; // scoped in function
}

console.log(foo); // ReferenceError: bar is not defined

let关键字将变量声明附加到包含它的任何块的范围。

报关单差异

letvar之间的另一个区别是声明/初始化顺序。在let声明之前访问由let声明的变量会导致 ReferenceError

console.log(a); // undefined
console.log(b); // ReferenceError: b is not defined

var a = 1;
let b = 2;

使用const

另一方面,使用ES6 const与使用let非常相似,但是一旦分配了值,就无法更改它。使用const作为不可变值,以防止意外重新分配变量:

const num = 42;

try {
  num = 99;
} catch(err) {
  console.log(err);
  // TypeError: invalid assignment to const `number'

}

num; // 42

使用const分配现实生活中恒定的变量(例如冻结温度)。 JavaScript const并不是要更改不可更改的值,它与该值无关,const是为了防止将另一个值重新分配给变量并将该变量设置为只读。但是,可以随时更改值:

const arr = [0, 1, 2];
arr[3] = 3; // [0, 1, 2, 3]

为防止值被更改,请使用Object.freeze()

let arr = Object.freeze([0, 1, 2]);
arr[0] = 5;

arr; // [0, 1, 2]

letFor循环一起使用:

let循环的标题中,for确实有用的一种特殊情况:

for (let i = 0; i <= 5; i++) {
  console.log(i);
}

// 0 1 2 3 4 5

console.log(i); // ReferenceError, great! i is not global

这也可以应用于其他循环,例如for ... infor ... of

答案 8 :(得分:0)

Var

The var keyword was introduced with JavaScript. 
It has global scope.    
It can be declared globally and can be accessed globally.   
Variable declared with var keyword can be re-declared and updated in the same scope.
Example:
function varGreeter(){
  var a = 10;        
  var a = 20; //a is replaced
  console.log(a);
}
varGreeter();

它被吊起了。

Example:
{
  console.log(c); // undefined. 
  //Due to hoisting
  var c = 2;
}

The let keyword was added in ES6 (ES 2015) version of JavaScript.
It is limited to block scope.
It can be declared globally but cannot be accessed globally.
Variable declared with let keyword can be updated but not re-declared.
Example:
function varGreeter(){
  let a = 10;        
 let a = 20; //SyntaxError: 
 //Identifier 'a' has already been declared
  console.log(a);
}
varGreeter();

它没有被吊起。

Example:
{
  console.log(b); // ReferenceError: 
  //b is not defined
  let b = 3;
}

全局对象属性

  var no1 = "123";  // globally scoped
  let no2 = "789"; // globally scoped

  console.log(window.no1); // 123
  console.log(window.no2); // undefined

重新声明:

“严格使用”;

  var name= "Keshav";
  var name= "Keshav Gera"; // No problem, 'name' is replaced.

  let surname= "Rahul Kumar";
  let surname= "Rahul Khan "; // SyntaxError: Identifier 'surname' has already been declared

起吊

function run() {
    console.log(name); // undefined
    var name= "Keshav";
    console.log(name); // Keshav
}

 run();

 function checkHoisting() {
     console.log(name); // ReferenceError
     let name= "Keshav";
     console.log(name); // Keshav
 }
 checkHoisting();

注意:在使用var的情况下,您将无法定义;在使用var的情况下,您将获得参考错误

const

It allows you to be immutable with variables.

必须初始化常量声明

const name; // ERROR: const declarations must be initialized

A const is block scoped like we saw with let:+

const num = 10;
if (true) {
 const num = 20; // Allowed as its a new variable limited to this `if` block
}

答案 9 :(得分:0)

  • var声明是全局范围的或函数范围的,而let和 const是块作用域的。

  • var变量可以在其范围内进行更新和重新声明;让 变量可以更新,但不能重新声明;常量变量不能更新或重新声明。

  • 它们都被吊在其作用域的顶部。但是虽然var 变量使用undefined初始化,let和const变量是 尚未初始化。

  • 虽然可以在不初始化的情况下声明var和let,但是const 必须在声明期间初始化。