Javascript 为什么它被称为函数表达式而不是函数声明?
我开始学习React,现在我又回到JavaScript中一些更基本的概念上来 我已经了解了函数表达式和函数声明之间的区别,但函数表达式为什么不被称为函数声明仍然让我感到困惑 如果这是一个变量声明:Javascript 为什么它被称为函数表达式而不是函数声明?,javascript,variables,expression,Javascript,Variables,Expression,我开始学习React,现在我又回到JavaScript中一些更基本的概念上来 我已经了解了函数表达式和函数声明之间的区别,但函数表达式为什么不被称为函数声明仍然让我感到困惑 如果这是一个变量声明: constfoo=5; 那为什么这叫做函数表达式呢 const bar=函数(){ //一些代码 }; 在第二个示例中,不是声明了“const bar”吗?为什么函数表达式和函数声明的命名方式是这样的?为什么函数表达式不称为函数声明,反之亦然 那为什么这叫做函数表达式呢 给变量赋值实际上是一个表达
constfoo=5;
那为什么这叫做函数表达式呢
const bar=函数(){
//一些代码
};
在第二个示例中,不是声明了“const bar”吗?为什么函数表达式和函数声明的命名方式是这样的?为什么函数表达式不称为函数声明,反之亦然
那为什么这叫做函数表达式呢
给变量赋值实际上是一个表达式。在您的示例中,这是一个表达式。您还声明了foo
,但它仍然是一个表达式
类似地,另一个示例const bar=function(){}
被称为函数表达式,以区分函数声明和函数表达式
函数表达式
const bar = function() {
// Some code
};
vs函数声明
function foo() {
// Some code
};
有趣的问题。措辞可能有软边界,这是造成这种混乱的部分原因 首先是一些粗略的定义:
- 表达:我认为最好用一个例子来思考这个问题
是一个表达式,因为您可以继续对它执行其他操作,如2*2
<另一方面,如果(…)不是javascript中的表达式,则它不会解析为一个值,您可以在该值中对其执行进一步的操作。如果(…){…}/2,则执行2*2-3
是无效的。这个“定义”有一些漏洞,但对于这个答案来说应该足够好了
- 声明:声明只是声明要使用某个变量名。因此,在您使用
的示例中,实际声明的是const foo=5
部分,const foo
只是初始化声明=5
记住这一点,让我们考虑两个函数的例子,看看这个术语是如何在这些例子中发挥作用的:
const g=function(){}
const g
。我们还看到有一个函数被创建并分配给g。我们用function(){}
的结果做了一些事情(我们将它分配给某个对象),这意味着javascript将把它解释为函数表达式
函数f(){}
函数f(){}
之前添加了一个+
,那么您将导致javascript将其解释为一个表达式,并且这些功能将被禁用。您可以在开发工具中尝试它-放入+函数f(){}
或const g=function f(){}
,f将保持未定义状态
javascript在不同的上下文中对function关键字的处理方式不同,这一事实是这种语言选择的核心。你几乎可以认为“function”关键字有两种不同的含义,所选择的含义取决于上下文。任何时候函数在表达式上下文中使用或未命名时,它都采用“表达式”形式,我们称之为“函数表达式”。否则,它将采用包含一些额外特性的替代形式,比如将函数名声明为局部变量。这可能就是为什么我们将这种替代形式称为函数声明。然而,正如OP正确指出的那样,即使使用const f=function(){}
,声明仍在发生,而不是通过function
关键字发生
脚注:对于像
+函数f(){}
这样的例子,f不会被定义在与g相同的范围内,但它确实是在f的主体内定义的。换句话说,任何命名函数表达式都在其自身的主体中声明其名称。web上有一些相关资源,包括。const bar
初始化是一个函数表达式,因为初始化声明变量的任何东西都是一种或另一种形式的表达式。const foo
是变量声明5
是一个表达式,而不是声明。考虑<代码> const FoO=1+1 < /COD>。显然,1+1
是一个需要与evaluatedRelated相关的表达式:。第一个代码块是StatementList→ 语句列表项→ 宣言→ 词汇退化→ LetOrConst绑定列表→ <代码>常量→ <代码>常量绑定标识符初始值设定项→ <代码>常量标识符=赋值表达式→ [跳过20个步骤]→ <代码>常量foo=PrimaryExpression→ <代码>常量foo=Literal→ <代码>常量foo=NumericLiteral→ [跳过4个步骤]→ <代码>常量foo=5。第二个块在文本处发散→ 函数表达式→ 等等,看。函数声明来自于声明→ 非常细微的挑剔:一些表达式仍然依赖于上下文;不能任意组合表达式。例如:await x
是一个表达式,但是()=>await x
无效,因为await
不是直接在异步
函数中使用的。另外,整个const foo=5
是一个声明const foo=5
来自const
Identifier=
AssignmentExpression,它派生自cons