var
基础
在函数作用域中使用 var 声明一个变量,则该变量属于当前函数作用域,如果声明在任何函数外的顶层作用语,则变量属于全局变量,如下所示
1 | var value1 = 'tom'; // 全局变量 |
在函数作用域中省略 var 声明一个变量时,那么该变量变成全局变量,若全局中存在该变量,则更新全局变量的值,如下所示
1 | var value1 = 'tom'; |
var 在块级作用域中,声明的变量是全局变量,即在块级作用域外也可以访问,如下所示
1 | for (var i = 0; i < 5; i++) { |
注意:var 声明的变量存在提升
提升
提升是指不管 var 声明的变量在作用域的那个位置,该变量都属于整个作用域,在当前作用域的各个地方都可以访问到,如下所示
1 | console.log(value); // undefined |
1 | var value1 = 'tom'; |
在上述代码块中,changeVal 函数中的 if 条件不管是真还是假,其输出都是 undefined
let 和 const
let
let 的声明存在以下特征
let声明的变量具有块级作用域的特征let声明的变量在同一作用域下不能重复声明let声明的变量不存在提升,即let声明存在暂时性死区
如下几个例子所示
1 | // 1,let声明的变量具有块级作用域的特征 |
1 | // 2,let声明的变量在同一作用域下不能重复声明 |
1 | // 3,let声明的变量不存在提升,即let声明存在暂时性死区 |
const
const 除了具有上述 let 的特点外,还有以下特征
const用于定义常量,不可更改const定义的常量必须初始化
如下几个例子所示
1 | // 1,const用于定义常量,不可更改 |
1 | // 2,const定义的常量必须初始化 |
var 和 let的区别
var 和 let 的区别,其例子如下所示
1 | for (var j = 0; j < 5; j++) { |
上述代码中,由于 setTimeout 是一个异步且采用 var 定义的 j 是一个全局变量,j 的值会覆盖已有的值,所以其输出为 5,5,5,5,5。
1 | for (let i = 0; i < 5; i++) { |
上述代码中,for 循环中采用了 let 声明循环变量 i,所以每一个循环都有自己的作用域,其值不会被覆盖,所以其值输出为 0,1,2,3,4.
总结
var可重复声明变量,let和const在同一作用域不允许重复声明var存在提升现象,let和const不存在var和let定义的变量可修改,const不可以const声明的值时必须初始化,let和var不需要