您的位置 首页 > 德语词汇

variables是什么意思?用法、例句?深入理解JS:var、let、const的异同

今天给各位分享variables是什么意思?用法、例句的知识,其中也会对深入理解JS:var、let、const的异同进行解释,如果能碰巧解决你现在面临的问题,别忘了关注本站,现在开始吧!

var、let和const都是JavaScript中用来声明变量的关键字,并且let和const关键字是在ES6中才新增的。既然都是用来声明变量的,那它们之间有什么区别呢?让我们来一探究竟。

2.var与let的区别

variables是什么意思?用法、例句?深入理解JS:var、let、const的异同

用var声明的变量的作用域是它当前的执行上下文,即如果是在任何函数外面,则是全局执行上下文,如果在函数里面,则是当前函数执行上下文。换句话说,var声明的变量的作用域只能是全局或者整个函数块的。

而let声明的变量的作用域则是它当前所处代码块,即它的作用域既可以是全局或者整个函数块,也可以是if、while、switch等用{}限定的代码块。

另外,var和let的作用域规则都是一样的,其声明的变量只在其声明的块或子块中可用。

functionvarTest(){\nvara=1;\n\n{\nvara=2;//函数块中,同一个变量\nconsole.log(a);//2\n}\n\nconsole.log(a);//2\n}\n\nfunctionletTest(){\nleta=1;\n\n{\nleta=2;//代码块中,新的变量\nconsole.log(a);//2\n}\n\nconsole.log(a);//1\n}\n\nvarTest();\nletTest();\n

从上述示例中可以看出,let声明的变量的作用域可以比var声明的变量的作用域有更小的限定范围,更具灵活。

(2)重复声明

var允许在同一作用域中重复声明,而let不允许在同一作用域中重复声明,否则将抛出异常。

vara=1;\nvara=2;\n\nconsole.log(a)//2\n\nfunctiontest(){\nvara=3;\nvara=4;\nconsole.log(a)//4\n}\n\ntest()\n

let相关示例代码:

if(false){\nleta=1;\nleta=2;//SyntaxError:Identifier'a'hasalreadybeendeclared\n}\n

switch(index){\ncase0:\nleta=1;\nbreak;\n\ndefault:\nleta=2;//SyntaxError:Identifier'a'hasalreadybeendeclared\nbreak;\n}\n

从上述示例中可以看出,let声明的重复性检查是发生在词法分析阶段,也就是在代码正式开始执行之前就会进行检查。

(3)绑定全局对象

var在全局环境声明变量,会在全局对象里新建一个属性,而let在全局环境声明变量,则不会在全局对象里新建一个属性。

varfoo='global'\nletbar='global'\n\nconsole.log(this.foo)//global\nconsole.log(this.bar)//undefined\n

那这里就一个疑问,let在全局环境声明变量不在全局对象的属性中,那它是保存在哪的呢?

varfoo='global'\nletbar='global'\n\nfunctiontest(){}\n\nconsole.dir(test)\n

在Chrome浏览器的控制台中,通过执行上述代码,查看test函数的作用域链,其结果如图:

由上图可知,let在全局环境声明变量bar保存在[[Scopes]][0]:Script这个变量对象的属性中,而[[Scopes]][1]:Global就是我们常说的全局对象。

(4)变量提升与暂存死区

var声明变量存在变量提升,如何理解变量提升呢?

要解释清楚这个,就要涉及到执行上下文和变量对象。

在JavaScript代码运行时,解释执行全局代码、调用函数或使用eval函数执行一个字符串表达式都会创建并进入一个新的执行环境,而这个执行环境被称之为执行上下文。因此执行上下文有三类:全局执行上下文、函数执行上下文、eval函数执行上下文。

执行上下文可以理解为一个抽象的对象,如下图:

Variableobject:变量对象,用于存储被定义在执行上下文中的变量(variables)和函数声明(functiondeclarations)。

Scopechain:作用域链,是一个对象列表(listofobjects),用以检索上下文代码中出现的标识符(identifiers)。

thisValue:this指针,是一个与执行上下文相关的特殊对象,也被称之为上下文对象。

一个执行上下文的生命周期可以分为三个阶段:创建、执行、释放。如下图:

而所有使用var声明的变量都会在执行上下文的创建阶段时作为变量对象的属性被创建并初始化,这样才能保证在执行阶段能通过标识符在变量对象里找到对应变量进行赋值操作等。

而用var声明的变量构建变量对象时进行的操作如下:

上述过程就是我们所谓的“变量提升”,这也就能解释为什么变量可以在声明之前使用,因为使用是在执行阶段,而在此之前的创建阶段就已经将声明的变量添加到了变量对象中,所以执行阶段通过标识符可以在变量对象中查找到,也就不会报错。

console.log(a)//undefined\n\nvara=1;\n\nconsole.log(a)//1\n

let声明变量存在暂存死区,如何理解暂存死区呢?

其实let也存在与var类似的“变量提升”过程,但与var不同的是其在执行上下文的创建阶段,只会创建变量而不会被初始化(undefined),并且ES6规定了其初始化过程是在执行上下文的执行阶段(即直到它们的定义被执行时才初始化),使用未被初始化的变量将会报错。

letandconstdeclarationsdefinevariablesthatarescopedtotherunningexecutioncontext’sLexicalEnvironment.ThevariablesarecreatedwhentheircontainingLexicalEnvironmentisinstantiatedbutmaynotbeaccessedinanywayuntilthevariable’sLexicalBindingisevaluated.AvariabledefinedbyaLexicalBindingwithanInitializerisassignedthevalueofitsInitializer’sAssignmentExpressionwhentheLexicalBindingisevaluated,notwhenthevariableiscreated.IfaLexicalBindinginaletdeclarationdoesnothaveanInitializerthevariableisassignedthevalueundefinedwhentheLexicalBindingisevaluated.

在变量初始化前访问该变量会导致ReferenceError,因此从进入作用域创建变量,到变量开始可被访问的一段时间(过程),就称为暂存死区(TemporalDeadZone)。

console.log(bar);//undefined\nconsole.log(foo);//ReferenceError:fooisnotdefined\n\nvarbar=1;\nletfoo=2;\n

示例代码2:

varfoo=33;\n{\nletfoo=(foo+55);//ReferenceError:fooisnotdefined\n}\n

注:首先,需要分清变量的创建、初始化、赋值是三个不同的过程。另外,从ES5开始用词法环境(LexicalEnvironment)替代了ES3中的变量对象(Variableobject)来管理静态作用域,但作用是相同的。为了方便理解,上述讲解中仍保留使用变量对象来进行描述。

3.let与const异同

const与let很类似,都具有上面提到的let的特性,唯一区别就在于const声明的是一个只读变量,声明之后不允许改变其值。因此,const一旦声明必须初始化,否则会报错。

leta;\nconstb="constant"\n\na="variable"\nb='change'//TypeError:Assignmenttoconstantvariable\n

如何理解声明之后不允许改变其值?

其实const其实保证的不是变量的值不变,而是保证变量指向的内存地址所保存的数据不允许改动(即栈内存在的值和地址)。

JavaScript的数据类型分为两类:原始值类型和对象(Object类型)。

对于原始值类型(undefined、null、true/false、number、string),值就保存在变量指向的那个内存地址(在栈中),因此const声明的原始值类型变量等同于常量。

对于对象类型(object,array,function等),变量指向的内存地址其实是保存了一个指向实际数据的指针,所以const只能保证指针是不可修改的,至于指针指向的数据结构是无法保证其不能被修改的(在堆中)。

关于本次variables是什么意思?用法、例句和深入理解JS:var、let、const的异同的问题分享到这里就结束了,如果解决了您的问题,我们非常高兴。

本站涵盖的内容、图片、视频等数据,部分未能与原作者取得联系。若涉及版权问题,请及时通知我们并提供相关证明材料,我们将及时予以删除!谢谢大家的理解与支持!

Copyright © 2023