概述:
ES6之前的版本用var声明变量,且不支持块级作用域
JS中变量的实际创建位置取决于如何声明该变量
ES6里面增加了两个关键字const和let用于控制作用域
作用域:限制变量的访问区域
let
let:识别块作用域,只在块作用域里面使用
var允许变量提升,变量提升的是声明,不包括赋值的部分
let的语法与var作比较:
1.ES6规定,如果区块中存在let和const命令,则这个区块对这些命令声明变量冲一开始就形成封闭作用域。
暂时性死区:let到其上面块之间的用到了let声明的变量的代码
2.let不允许重复声明,在同一作用域下,两个let也不可以
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-numemIQG-1618993759578)(C:\Users\97950\AppData\Roaming\Typora\typora-user-images\image-20210311144300412.png)]
3.let支持块作用域
作用域
1.变量或函数在起作用的区域
2.JS采用的是词法作用域(也叫静态作用域,因为代码是静态的),即变量的作用域取决于变量所在的代码区域
3.ES6新增了“块作用域”,也包含ES5中的全局作用域和局部作用域
全局作用域:一个浏览器窗口
函数作用域:创建一个函数
块作用域:由{}界定的代码范围,let声明的变量具备可访问该作用域
作用域链:每一段JS代码(全局或函数)都有一个与之关联的作用域链
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-WfVhaNow-1618993759583)(file:///C:\Users\97950\Documents\Tencent Files\979508618\Image\C2C\635D31C7C76901077E8366C573DCC171.jpg)]
ES5会变量提升,造成一些问题;内部变量覆盖外部变量
会被外部任务使用或修改,把用来计数的循环变量泄露为全局变量
[外链图片转存失败,源站可能有防盗链机制,建议将图片保存下来直接上传(img-gBiY26I5-1618993759584)(file:///C:\Users\97950\Documents\Tencent Files\979508618\Image\C2C\73688AA41F60317B99A2AED2C24C9128.jpg)]
let为JS新增了块级作用域;
ES6允许块级作用域任意嵌套,一对{}即为一个块级
内层作用域可以定义与外层作用域同名变量
ES5中用IIFE(立即执行匿名函数)
const
用来声明一个只读的常量,一旦声明,其值不能改变且必须立即初始化,初始化之后不能被改变
除此之外,与let一致
const foo = {y:100}
foo.x = 12; //不会报错,因为foo里面保存的是对象的引用,然后可以对对象操作
console.log(foo);
foo = {n:1000};//错误不能对foo改变
小结:
浏览器顶层对象为window,Node为global
var和function定义的全局对象会关联到顶层对象,let和const不会
ES6为ES5提供了良好的兼容性
用于let和const能提供更好的作用域识别,建议尽量采用let声明变量,const声明常量