在过去的几个小时中,我一直试图找到3个区别,而不仅仅是区别,我还一直在尝试找出哪种是同义词,MDN调用全部声明"语句",所以我认为这是事实。但是,我读过的任何文章都没有给我一个备忘单,以区分3(或2,表达式与语句)。
我在语句中注意到的是,它们都以某种方式涉及一个特殊的JavaScript关键字,例如break
或for
或var
。这些文章说,表达式评估某物,而语句执行动作。那是什么函数?它是语句表达混合动力(因为它在调用时都执行动作并返回值)吗?目前,我假设事实并非如此,因为函数调用不涉及JavaScript关键字。
然后有声明,每个声明也是一个声明吗?
我也知道诸如20 + 5 * 2 / 3;
之类的表达语句,但是这些实际上没有用吗?为什么有人会用这样的行污染他们的代码?
如果有人可以提出上述问题(或至少其中一些问题),或者有人可以为我提供某种备忘单,我会感到非常高兴。为什么在如此受欢迎的语言中似乎很简单的主题材料很少?
这些术语都有标准定义,所有语言都有,包括JS,关注。我对它们的看法如下:
-
表达式会产生一个值,并且可以在预期值的任何地方写入值。
-
另一方面的说法是独立执行单位。它不会返回任何东西。
-
声明是一个陈述,其中值分配给变量。
-
所有声明都是语句,但并非所有语句都是声明。
-
大多数语句和所有声明都包含表达式。
Javadoc还提供了漂亮,简洁的定义:
表达式是由变量,运算符和方法调用组成的构造,它是根据语言语法构造的,它评估为单个值。
语句大致等于自然语言的句子。声明形成了执行的完整单位。
现在,您关于关键字所涉及的理论不正确。这是一个包括关键字的语句:
break;
这不是:
foo();
在第一个示例中,我执行了break
,而在第二个示例中,我称为函数。两者都是陈述,但是只有一个包括任何特殊关键字。
函数不是语句。函数呼叫是上述语句。对于返回某些内容的函数,调用也可以是声明:
var bar = foo();
,对于您的最后一个问题,这是因为这仅仅是语义问题的原因。人们不关注这些术语的确切定义。
为了进一步澄清,我建议您查看Axel Rauschmayer的这篇博客文章,该文章专门讨论了JS中的语句和表达式之间的区别。
在过去的几个小时中,我一直试图找到3个区别,而不仅仅是区别,我还试图找出哪种是同义词,mdn调用所有声明"语句",所以我假设是的。
声明是在程序执行之前在编译/加载时间中"声明"变量名称"声明"的任何构造。因此,所有在其各自的范围中声明的名称都已提前已知。
陈述和表达式彼此不同,因为前者没有产生值的值,而后者则没有。因此,可以在预期值的任何地方使用表达式,并且在这些地方不得使用语句。
表达式语句是该语句是单个表达式的一种,或者在需要零或更多子表达的表达式中包含一些。虽然表达式产生结果,但该语句不会。
这是一个表达式:
x = foo() + 2
可以通过在末端添加半隆来明确显示一个完整的表达式语句。
x = foo() + 2;
第一个示例可以包裹在一组Parens中,因为Parens作为分组操作员期望表达式,通常以逗号操作员加入的几种表达式提供。
第二个示例不能包裹在Parens(如果包括分号)中,因为它是一个陈述,并且不会产生一个值,分组运营商期望将其作为其自身的价值接收和返回。
我在语句中注意到的是,它们都以某种方式涉及一个特殊的JavaScript关键字,例如Break或for或var。
大多数语句确实涉及关键字,而不是全部。最值得注意的是,块语句没有关键字。相反,它使用一组卷曲支架来界定其开始和结束。
文章说,表达式评估某物,而语句执行动作。那是什么函数?它是语句表达混合动力(因为它在调用时都执行动作并返回值)吗?目前,我假设事实并非如此,因为函数调用不涉及JavaScript关键字。
JS中有三种功能。如果您要谈论的是使用函数关键字的内容,则可以根据其上下文是声明或表达式。
如果在预期表达式的位置使用该函数,则将其评估为返回新功能对象的表达式。如果不是这样,则预计将是一份声明,它基本上会创建一个带有分配给其函数对象的变量。作为声明,函数名称是必需的(对于变量名称)。作为表达式,它是可选的。
我也知道诸如
20 + 5 * 2 / 3;
之类的表达语句,但实际上不是无用的吗?为什么有人会用这样的行污染他们的代码?
如果忽略了结果值,则鉴于该示例,这将是没有用的。但这是另一个表达式语句。
foobar();
现在,我们从功能调用中产生了副作用,最有可能且有用。
让我们先谈谈表达式。正如您所说,表达式是评估价值的东西。函数是一个值。另一方面,函数呼叫是一个表达式。
我不同意陈述的表征是"执行动作"的东西。如您所说,调用功能涉及运行该功能体,该功能由语句和声明组成,因此它在"内部"执行操作。
更好地看待它的方法是表达,语句和声明是句法类别。它们是由于试图描述JavaScript语法的结构而产生的。参见例如Ecmascript 8关于表达式,语句和声明的规范。
像 20 + 5 * 2 / 3;
这样的表达式语句确实没有用,因为它没有效果,而陈述的唯一点是其效果。但是还有其他更有用的表达语句:
- 函数调用:
foo();
- 分配:
x = 42;
(=
是操作员,可以在表达式中使用) - 增量/减少:
i++;
(同样,++
是操作员)
表达语句以外的其他语句倾向于从一个特殊的关键字开始,以避免句法歧义:解析器希望能够从一开始就可以说出它正在处理哪种构造。因此我们得到:
- 如果语句:
if (EXPR) STMT
- 在语句中:
while (EXPR) STMT
- 返回语句:
return;
或return EXPR;
- 等。
但是,有些语句不会以关键字开头:
- 空语言:
;
- 一个块:
{ ... }
最后,声明。在JavaScript中,语句和声明之间的区别在某种程度上是任意的。语法区分两者,但实际上,您通常可以对其进行相同的对待(例如,块语句的内容定义为语句列表list项目的序列,并且语句列表项目定义为要么是声明或声明)。声明包括:
- 函数声明:
function foo() { ... }
(包括生成器(function* foo() { ... }
)和异步功能(async function foo() { ... }
)等变体) -
let
和const
-
class
声明
(但由于某种原因,var foo;
被归类为语句,而不是声明。)