JavaScript中var、let和const的区别
- A
在网络上,我们初学js,遇到的第一个声明变量的方法基本上都是var吧,但是在ES6(ES2015)之后,官方新增加了两个重要的 JavaScript 声明变量关键字: let 和 const。
所以截止目前为止,JavaScript中共有三种声明变量的方式:var、let、const;那么,我今天就在本文中介绍一下这三者的区别:
一、var
1.如果使用关键字 var 声明一个变量,那么这个变量就属于当前的函数作用域,如果声明是发生在任何函数外的顶层声明,那么这个变量就属于全局作用域。
2.var定义的变量在之后可以随意修改,如果不初始化就会默认输出 undefined,并不会报错。
3.var只有函数作用域,没有块级作用域。
4.var相比let就是管的比较宽,他的值可以被内部修改。
var a = 1; //此处声明的变量a为全局变量 function gatherso(){ var a = 2;//此处声明的变量a为函数foo的局部变量 console.log(a);//2 } gatherso(); console.log(a);//1
如果在声明变量时,省略 var 的话,该变量就会变成全局变量,如全局作用域中存在该变量,就会更新其值,如:
var a = 1; //此处声明的变量a为全局变量 function gatherso(){ a = 2;//此处的变量a也是全局变量 console.log(a);//2 } gatherso(); console.log(a);//2
全局变量:在函数外定义的变量,作用域是整个代码文件。
局部变量:在函数内定义的变量,作用域是当前的函数内部。
二、let
1.let 声明的变量只在 let 命令所在的代码块内有效,它是一个块级作用域。
let a = 666; console.log("函数外let 定义a:" + a); // 函数外let 定义a:666 function gatherso(){ let a = 888; console.log("函数内let 定义a:" + a);// 函数内let 定义a:888 } gatherso(); console.log("函数调用后let 定义a为函数内部修改值:" + a); // 函数调用后let定义a为函数内部修改值:666
2.在同一个块级作用域,不能重复声明变量。
let a = 1; let a = 2; console.log(a);//Identifier 'a' has already been declared
3.let 声明的变量不存在变量提升,换一种说法,就是 let 声明存在暂存死区。
function gatherso(){ let n = 1; if (true) { let n = 2; } console.log(n); //值不会被修改,输出1 } gatherso(); if(1){ let b = 100; } console.log(b);//错误 ReferenceError: b is not defined //因为let的块级作用域,所以b变量只存在与if内部
4.不能提前声明变量否则报错
let a = 1; console.log(a);//1 console.log(b);//Uncaught ReferenceError: b is not defined let b = 2;
var其实是网景公司的一个小小的失败品,所以在ES6中才出现了let,下面这个十分有趣的例子可以清楚的表示var的毒性
for (var i = 0; i < 10; i++) { setTimeout(function(){ console.log(i); },100) };
该代码运行后,会在控制台打印出10个10.若将修改为let,则该代码运行后,就会在控制台打印出0-9。
三、const
1.const 的声明方式,除了具有 let 的上述特点外,其还具备一个特点,即 const 定义的变量,一旦定义后,就不能修改,即 const 声明的为常量,也就是php里面的define。
2.const用来定义常量(可以是字符串,数组,函数,对象等),并且初始值不可为空,但他并不是不可更改的:
const c;//会产生报错. const d = 1;//正确 const arr = [1, 2]; arr.push(1);//正确 [1, 2, 1] arr[0] = 3;//正确 [3, 2, 1] arr = [];//错误TypeError: invalid assignment to const `arr'
由上可见,如果有需要,可以改变const里所存储的值,但它的指向空间是无法操作的,更准确的来说,是 const 声明创建一个值的只读引用。但这并不意味着它所持有的值是不可变的,只是变量标识符不能重新分配。。
3.const与let一样,都是块级作用域,只能在块作用域里访问,存在暂时性死区,不存在变量声明提前,不允许重复定义。
四、总结
1.var 声明的变量属于函数作用域,let 和 const 声明的变量属于块级作用域;
2.var 存在变量提升现象,而 let 和 const 没有此类现象;
3.var 变量可以重复声明,而在同一个块级作用域,let 变量不能重新声明,const 变量不能修改。