Javascript 词法环境和函数作用域

声明:本页面是StackOverFlow热门问题的中英对照翻译,遵循CC BY-SA 4.0协议,如果您需要使用它,必须同样遵循CC BY-SA许可,注明原文地址和作者信息,同时你必须将它归于原作者(不是我):StackOverFlow 原文地址: http://stackoverflow.com/questions/12599965/
Warning: these are provided under cc-by-sa 4.0 license. You are free to use/share it, But you must attribute it to the original authors (not me): StackOverFlow

提示:将鼠标放在中文语句上可以显示对应的英文。显示中英文
时间:2020-08-23 10:47:31  来源:igfitidea点击:

Lexical environment and function scope

javascriptfunction

提问by Aljo?a Srebotnjak

Is lexical environment and scope in javascript one and the same thing?

javascript 中的词法环境和作用域是一回事吗?

采纳答案by adnan2nd

Giving the answer based on what I have just learned from 'Secrets of the Javascript Ninja, 2/e' --

根据我刚刚从“Javascript Ninja 的秘密,2/e”中学到的知识给出答案——

They are different concepts but related, we need to define a related concept - Execution Context & it's stackto understand.

它们是不同的概念但相关,我们需要定义一个相关的概念 -执行上下文及其要理解的堆栈

Execution Context& Execution Context stack: Execution contextis the internal javascript construct to track execution of a function or the global code. The js engine maintains a stack data structure - execution context stackor call stack, which contains these contexts and the global execution contextstays at the bottom of this stack. And a new execution context is created and pushed to the stack when execution of a function begins. A particular execution context tracks the pointer where statement of the corresponding function is being executed. An execution context is popped from the stack when corresponding function's execution is finished.

执行上下文执行上下文堆栈执行上下文是用于跟踪函数或全局代码执行的内部 javascript 构造。js 引擎维护着一个栈数据结构——执行上下文栈调用栈,其中包含了这些上下文,全局执行上下文停留在这个栈的底部。当函数开始执行时,会创建一个新的执行上下文并将其推送到堆栈中。特定的执行上下文跟踪正在执行相应函数的语句的指针。当相应函数的执行完成时,执行上下文从堆栈中弹出。

Lexical Environment: it's the internal js engine construct that holds identifier-variable mapping. (here identifierrefers to the name of variables/functions, and variableis the reference to actual object [including function type object] or primitive value). A lexical environment also holds a reference to a parent lexical environment.

词法环境:它是保存标识符变量映射的内部 js 引擎构造。(这里标识符是指变量/函数的名称,变量是对实际对象[包括函数类型对象]或原始值的引用)。词法环境还持有对父词法环境的引用。

Now, for every execution context-- 1)a corresponding lexical environment is created and 2)if any function is created in that execution context, reference to that lexical environment is stored at the internal property ( [[Environment]]) of that function. So, every function tracks the lexical environment related to the execution context it was created in.

现在,对于每一个执行上下文- 1)对应的词法环境被创建和2)如果在该执行上下文创建的任何功能,参照该词法环境存储在内部属性([[环境]]那的)功能. 因此,每个函数都会跟踪与其创建的执行上下文相关的词法环境。

And every lexical environment tracks its parent lexical environment (that of parent execution context). As a result, every function has a chain of lexical environments attached to it. [Note: in js a function is an object, creating a function by a statement means creating an object of type Function. So like other objects, a function can hold properties both internal and user defined]

并且每个词法环境都跟踪其父词法环境(父执行上下文的词法环境)。因此,每个函数都有一个附加的词法环境链。【注:在js中函数就是对象,通过语句创建函数就是创建一个Function类型的对象。所以像其他对象一样,一个函数可以保存内部和用户定义的属性]

Scope: it's the language agnostic concept, to refer to the visibility of variables or functions to the executing code. In js a variable or function is visible to the executing code, if it is there in the current lexical environment or in the lexical-environment-chain of the enclosing function. In case of global code, the chain does not exist.

范围:它是语言不可知的概念,指的是变量或函数对执行代码的可见性。在 js 中,如果变量或函数存在于当前词法环境或封闭函数的词法环境链中,则变量或函数对执行代码是可见的。在全局代码的情况下,链不存在。

Hope, you understand now ..

希望,你现在明白了..

Note: similar to function's case, by the introduction of let and constin es6, when a block begins to execute (ifblock, for loopblock etc), a new lexical environment is also created having the parent function's lexical environment as parent.

注意:与函数的情况类似,通过在 es6 中引入let 和 const,当一个块开始执行时(if块、for 循环块等),也会创建一个新的词法环境,以父函数的词法环境为父。

回答by James Allardice

Here's what the spec says about lexical environments:

这是规范对词法环境的描述

A Lexical Environment is a specification type used to define the association of Identifiers to specific variables and functionsbased upon the lexical nesting structure of ECMAScript code. A Lexical Environment consists of an Environment Record and a possibly null reference to an outer Lexical Environment.

词法环境是一种规范类型,用于根据 ECMAScript 代码的词法嵌套结构定义标识符与特定变量和函数的关联。词法环境由环境记录和对外部词法环境的可能为空的引用组成。

Based on that, I would say yes, that's what people are usually talking about when they say "scope".

基于此,我会说是的,这就是人们在说“范围”时通常谈论的内容。

Although it could probably be argued that a "scope" is actually defined as a "Declarative Environment Record":

尽管可能会争论“范围”实际上被定义为“声明性环境记录”:

Each declarative environment record is associated with an ECMAScript program scope containing variable and/or function declarations. A declarative environment record binds the set of identifiers defined by the declarations contained within its scope.

每个声明性环境记录都与包含变量和/或函数声明的 ECMAScript 程序范围相关联。声明性环境记录绑定由包含在其范围内的声明定义的标识符集。

If you think of a "scope" as a thing that contains bindings between identifiers and values, then the 2nd definition probably fits better. If you think of it as something that is aware of its ancestor scopes, then the first definition fits better.

如果您将“范围”视为包含标识符和值之间的绑定的事物,那么第二个定义可能更适合。如果您将其视为知道其祖先作用域的东西,那么第一个定义更适合。

Edit: and a third option is "Execution Context".

编辑:第三个选项是“执行上下文”。

回答by poushy

Lexical Environment is the environment of the function where it is written. That is, the static order/place where it is situated, regardless from where it is called from.

词法环境是编写它的函数的环境。也就是说,它所在的静态顺序/地点,无论从哪里调用它。

Scope of a variable/function is basically the locations from where a variable is visible/accessible.

变量/函数的范围基本上是变量可见/可访问的位置。

Execution context is the status of the execution stack at any point during runtime. That is the current execution context.

执行上下文是运行时任何时候执行堆栈的状态。那就是当前的执行上下文。