ES6新特性之let、const、var的区别
特此说明: 借鉴阮一峰老师的ECMAScript 6 入门;传送门,MDN文档;传送门
let const var关键字
三个关键字的区别:
let | const | var | |
---|---|---|---|
变量提升 | × | × | √ |
全局变量 | × | × | √ |
重复声明 | × | × | √ |
重新赋值 | √ | × | √ |
只声明不初始化 | √ | × | √ |
暂时死区 | √ | √ | × |
块作用域 | √ | √ | × |
- 什么是变量提升
- var关键字声明的变量,无论实际声明的位置在何处,都会被视为声明在函数的顶部(如果声明不在任意函数内,则视为在全局作用域的顶部)
- JavaScript引擎的工作方式是,先预解析代码, 获取所有被声明的变量和函数声明,然后再一行一行地运行,这就使所有变量声明的语句,都会被提升到代码的头部,这就是变量提升
//var关键字声明时
console.log(b) //undefined
var b = 3;
console.log(b); // 3
上面代码首先在控制台显示未声明的变量,本来是错误的做法但是没有报错.因为JS的变量提升.真正运行的是以下代码
var b ;
console.log(b);
b = 1;
console.log(b);
- let声明的变量不会在作用域中被提升;在let声明之前的执行瞬间被称为”暂时性死区“,在此阶段引用任何后面才声明的变量都会抛出。
let a = 1;
console.log(a);//1
console.log(b);//Uncaught ReferenceError: b is not defined
let b = 2;
- 全局变量
- 使用let和const在全局作用域中声明的变量不会成为window对象的属性,var声明的变量则会。
//var关键字
var name = 'Yu';
console.log(window.name);//'Yu'
//let关键字
let age = 'Yu';
console.log(window.name);//undefined
- 重复声明
var
允许重复声明变量let
和const
在同一作用域不允许重复声明变量
// var关键字
var a = 10
var a = 20 // 20
// let关键字
let b = 10
let b = 20 // Identifier 'b' has already been declared
// const关键字
const c = 10
const c = 20 // Identifier 'c' has already been declared
- 重新赋值
var
和let
可以重新赋值const
声明一个只读的常量。一旦声明,常量的值就不能改变
// var关键字
var a = 10
a = 20
console.log(a) // 20
//let关键字
let b = 10
b = 20
console.log(b) // 20
// const关键字
const c = 10
c = 20
console.log(c) // Uncaught TypeError: Assignment to constant variable
- 只声明不初始化
- 在首次声明时
let
var
可以不赋值 const
声明必须赋值
- 暂时死区
- 什么是暂时性死区:
let
、const
关键字声明的变量会产生块级作用域,如果变量在当前作用域中被创建之前被创建出来,由于此时还未完成语法绑定,如果我们访问或使用该变量,就会产生暂时性死区的问题,由此我们可以得知,从变量的创建到语法绑定之间这一段空间,我们就可以理解为‘暂时性死区’ var
不存在暂时性死区let
和const
存在暂时性死区,只有等到声明变量的那一行代码出现,才可以获取和使用该变量
// var关键字
console.log(a) // undefined
var a = 10
// let关键字
console.log(b) // Cannot access 'b' before initialization
let b = 10
// const关键字
console.log(c) // Cannot access 'c' before initialization
const c = 10
- 块作用域
var
不存在块级作用域let
和const
存在块级作用域
// var关键字
{
var a = 20
}
console.log(a) // 20
// let关键字
{
let b = 20
}
console.log(b) // Uncaught ReferenceError: b is not defined
// const关键字
{
const c = 20
}
console.log(c) // Uncaught ReferenceError: c is not defined