Javascript Mozilla状态表达式也是语句。为什么?

Javascript Mozilla状态表达式也是语句。为什么?,javascript,Javascript,查看Mozilla的JavaScript指南中的以下文章: 表达式也被视为赋值语句。事实上,在第二篇文章中,我们可以读到“任何表达也是一种陈述”。由于熟悉其他编程语言,我认为表达式总是值,但它们从来不会像语句那样产生副作用。换句话说,7、7+8、“字符串”等都是表达式,因为它们不会改变状态,但a=7是一个语句,因为现在已经定义了一个变量(即状态已经改变) 为什么Mozilla不在JS中区分这两个词呢?我相信您对“表达式”和“语句”的理解过于字面化了。“表达式不改变任何状态”对编程语言来说是一

查看Mozilla的JavaScript指南中的以下文章:

表达式也被视为赋值语句。事实上,在第二篇文章中,我们可以读到“任何表达也是一种陈述”。由于熟悉其他编程语言,我认为表达式总是值,但它们从来不会像语句那样产生副作用。换句话说,7、7+8、“字符串”等都是表达式,因为它们不会改变状态,但a=7是一个语句,因为现在已经定义了一个变量(即状态已经改变)


为什么Mozilla不在JS中区分这两个词呢?

我相信您对“表达式”和“语句”的理解过于字面化了。“表达式不改变任何状态”对编程语言来说是一个非常严格的要求

思维实验:在
7+8
中,用函数调用替换
8

var globalVar = 0;
function my8() { 
  globalVar = globalVar + 1; 
  return 8;
} 
7+my8()
是语句还是表达式?这里没有发生明显的状态更改,但仍然
my8
执行状态更改。使用“无副作用”定义,如果不分析
my8
函数的代码,就无法确定
7+my8()
是语句还是表达式。当然,可以简单地禁止任何状态更改作为函数调用的一部分,但这不是JavaScript的方式

根据我的经验,大多数语言都将“返回值的所有内容”定义为表达式和语句,其他所有内容都定义为语句

要回答您的问题“为什么Mozilla不在JS中区分这两种语言?”

我想是的,但不是你想象的那样。要考虑“返回值的所有东西”,表达式似乎是最实用的方法。 同时作为语句和表达式的代码块之间也没有矛盾。这就是Javascript和许多其他语言的工作原理。当然,总是有可能在这两者之间划出一条更严格的界限

示例:

赋值返回值,因此这是可能的:

 a = b = c = 1;
它可以用更明显的形式书写:

 a = (b = (c = 1));
因此,赋值被认为是一个表达式(也是一个语句)

另一方面:

if (true) { };

不返回值(在Javascript中!),因此不是表达式(但仍然是一个语句)。

Mozilla确实区分了这两者,或者更确切地说是Javascript语法

Javascript的唯一“特殊”之处在于:

“任何表达式也是一个语句”

这意味着在语法中需要语句的地方,可以直接使用表达式(但不能反过来使用)。例如,以下是有效的Javascript,但在许多其他类似语言中无效:

if (true) "asfd"

鉴于语句不能用作表达式:

a = (if (true) 5)   // does not work "unexpected token 'if'"
他们在严格模式规范中使用了该“功能”,而没有引入新的关键字或语法-如果在函数体中添加表达式
“use strict”
,Javascript将在支持浏览器的严格模式下执行

虽然表达式的计算结果是一个值,但语句通常不会。大多数语句都会改变控制流,而表达式通常不会(尽管有人可能认为导致抛出异常的表达式也会改变控制流)。
在Javascript中,表达式构成所有语句的子集。

表达式是返回某些值的代码片段:

可以将表达式组合为一个复合表达式:

3 + 7; // 10
{}, []; // Array. Comma operator always returns result of right-most expression
语句是可以编译或解释的最小有效代码片段:

还可以将语句组合成复合语句:

check || func(); // valid js
{
    4 + 9;
    "block statement";
}
在Mozilla文档中,语句引用任何以分号(;)显式或隐式终止的(复合)语句

在某些编程语言中,上面的示例不进行编译或解释。其他语言可能不允许捕捉表达式的结果


Javascript的表达能力非常强,这就是为什么每个表达式都算作有效语句的原因。有些语句不是表达式,如break、return、while等。它们不返回任何值,但它们控制程序执行

请定义“状态更改”的含义,因为按照我的理解,您的第一个示例调用了一个函数,它是由两个语句组成的块(分配和返回)。也就是说,调用是一系列语句。代码生成一个值,但它也会递增globalVar。您的解释将语句描述为不返回值的所有语句,但Mozilla声明表达式也是语句。请解释这一矛盾。矛盾源于我的措辞不准确,抱歉。最后一句ce读起来像iff,而实际上我只是指if:)我重新措辞了它,还添加了一些其他想法返回值?它们不是简单地将名称指向值吗?请解释什么是语句,什么不是表达式。顺便说一句,您的第二个示例返回的是
语法错误:非法返回语句
3 + 7; // 10
{}, []; // Array. Comma operator always returns result of right-most expression
5; // valid js
check || func(); // valid js
{
    4 + 9;
    "block statement";
}
[,,[],[,[,,],,]]; // Array declaration whose reference is returned (and ignored)
// Multi-dimensional array with empty (undefined) elements