JavaScript 函数声明与函数表达式的区别及原理
本文详细解析JavaScript中函数声明与函数表达式的核心区别。重点阐述两者在变量提升、加载时机(解释期vs运行期)及调用限制上的不同,并结合执行上下文与激活对象概念,说明为何函数表达式在定义前调用会返回undefined。
函数声明与表达式的基本定义
这两种定义方式在开发中十分常见,但许多开发者可能并不清楚它们之间的具体差异以及底层的运行机制。
相关代码示例如下:
// 方式1
function func1(x,y){
// 具体实现代码
}
// 方式2
var func2 = function(x,y){
// 具体实现代码
}方式1属于典型的函数声明(Function declarations)。
方式2则是函数表达式(Function expressions),即将一个匿名函数赋值给变量。具体来说,方式2创建了一个形参为x和y的匿名函数,并将该函数的引用赋值给变量func2。
核心区别:命名与加载时机
两者的主要区别体现在以下几个方面:
第一,函数声明必须显式指定函数名,例如这里的func1;而函数表达式通常使用匿名函数。
第二,加载时机不同。方式1在代码执行之前(即解释期)就会被加载到当前作用域中;而方式2必须在代码执行到该语句时(即运行期)才会被加载。
调用顺序与变量提升现象
通过一个简单的示例即可直观理解它们在使用上的差异。
测试代码如下:
alert(func1); // 输出 func1 的源码字符串
alert(func2); // 输出 undefined
// 方式1
function func1(x,y){
// 具体实现代码
}
// 方式2
var func2 = function(x,y){
// 具体实现代码
}从输出结果可以看出,第一次弹出的是func1的源码,而第二次却是undefined。这表明,使用方式1(函数声明)定义的函数,可以在其定义语句之前被调用;而使用方式2(函数表达式)定义的函数,则不能在定义之前被调用,必须等待定义语句执行完毕后才能使用。
内部原理:执行上下文与激活对象
其内部机制涉及执行上下文(Execution context)及激活对象(Activation object)。若需深入了解底层原理,建议查阅EcmaScript 5相关文档。
近期观察到越来越多的开发者倾向于使用方式2来定义函数,尤其是在嵌套函数的场景中。不过,对于单纯定义独立函数的情况,个人仍更习惯使用方式1。
JS语法错误会阻止加载吗?区分SyntaxError与资源加载失败
2026-11-05 16:08:46
JavaScript常见SyntaxError语法错误排查与修复方法
2026-11-05 13:58:44
JS中slice、substring和substr截取字符串的区别
2026-11-05 13:43:47
JS 转 TS 手动迁移最佳实践:从配置 tsconfig 到消除 any 类型
2026-11-05 11:53:32
为什么JS数组push后得到的是数字而不是数组?
2026-11-05 09:59:18
