72

我已经阅读并通过自己的经验发现,JavaScript 没有块作用域。假设这种语言是出于某种原因设计的,你能向我解释一下这个原因是什么吗?

我在 Google 和这里​​查看过,但我发现的帖子只是重申 JS 具有函数作用域而不是块作用域,而没有解释原因。我很想知道为什么会这样。

4

4 回答 4

114

将我的评论转换为答案

创作者的选择:我在 Brendan 上发了推文,得到了以下答案

@mplungjan 10 天没有为块范围留出时间。90 年代中期的许多“脚本语言”的范围也很少,后来发展得更多。


也就是说,这里有一些相关点:

重要提示:ECMAScript2015(第 6 版)之前的 JavaScript 没有块作用域。在块中引入的变量的作用域是包含函数或脚本,设置它们的效果会持续到块本身之外。换句话说,块语句不引入范围。尽管“独立”块是有效的语法,但您不想在 JavaScript 中使用独立块,因为如果您认为它们在 C 或 Java 中执行类似块的操作,它们不会按照您的想法执行。

我们可以通过创建新函数并立即调用它们来人为地引入作用域

let并且const声明的变量被提升,但它们没有undefined以相同的方式初始化var。因此,在赋值之前引用let或声明的变量会引发 ReferenceError。const

在同一块范围内重新声明同一变量会引发 SyntaxError。

于 2013-06-26T05:12:00.503 回答
15

截至 2015 年的新答案。ES6 确实具有使用letandconst关键字定义变量的块范围。

于 2015-05-13T09:34:58.070 回答
12

由于以下原因,没有实现块范围:

  1. 它使语言更容易实现。JavaScript 最初被设计为一种用于编写交互式 Web 应用程序的语言。因此,它需要小且易于实施。
  2. 块作用域给 JavaScript 等动态语言带来了性能损失。这是因为当您尝试访问不在当前作用域中的某个变量时,JavaScript 首先检查当前作用域,然后检查父作用域,依此类推,直到找到变量或到达末尾。因此,块作用域的引入将使循环和嵌套循环中的变量访问非常慢。
  3. 缺少块作用域使编写程序更容易。例如,假设您只想在某个条件为真时创建一个变量。在 JavaScript 中您需要做的就是在if语句中声明和定义变量。在像 C 这样的语言中,您必须在语句之外声明变量并在if语句中定义它if
  4. 缺少块作用域允许提升声明。这在函数声明的情况下特别有用。例如看这个小提琴: http: //jsfiddle.net/L6SgM/(但是请注意,这个例子在 Firefox 中不起作用)。
  5. 由于 JavaScript 支持一流的函数表达式,我们不需要块作用域。可以使用立即调用的函数表达式来模拟它们。
于 2013-06-26T05:31:06.200 回答
0

有很多原因,但想到的一些原因是帮助解析/调试使用对象文字(有时看起来像一个块)的代码,并简化局部变量的垃圾收集。

我希望承诺的支持(在此讨论,例如,http ://esdiscuss.org/notes/2012-07-25 )结果是真实的,因为使用像i这样的变量是非常方便的单回路。

于 2013-06-26T04:50:14.013 回答