定义函数的方式有两种:一种是函数声明,另一种是函数表达式。
一、两者的语法
函数声明的语法:
function functionName(arg0, arg1, arg2){
//函数体
}
函数表达式的语法:
var functionName = function(arg0, arg1, arg2){
//函数体
}
因为function关键字后面没有标识符,这种情况下创建的函数叫做匿名函数(anonymous function,有时也叫拉姆达函数)。匿名函数的name属性是空字符串。
二、两者区别
在ECMAScript中,有两个最常用的创建函数对象的方法,即使用函数表达式或者使用函数声明。对此,ECMAScript规范明确了一点,即是,即函数声明 必须始终带有一个标识符(Identifier),也就是我们所说的函数名,而函数表达式则可以省略。
关于函数声明,它的一个重要特征就是函数声明提升(function declaration hoisting),意思是在执行代码之前会先读取函数声明。这就意味着可以把函数声明放在调用它的语句的后面。
sayHi();
function sayHi(){
alert("Hi");
}
而函数表达式与其他表达式一样,在使用前必须先赋值。以下代码就会发生错误。
sayHi();
var sayHi = function(){
alert("Hi!");
}
三、两者的转换
为了提高开发效率,开发者会使用IFEE(immediately-invoked function expression,即时执行方法)
那么为什么要 IIFE?
- 传统的方法啰嗦,定义和执行分开写;
- 传统的方法直接污染全局命名空间(浏览器里的
global
对象,如window
)
传统的写法:
function foo() {...} // 这是定义,Declaration;定义只是让解释器知道其存在,但是不会运行。
foo(); // 这是语句,Statement;解释器遇到语句是会运行它的。
IIFE的写法:
(function foo() {...}) // 这里是故意换行,实际上可以和下面的括号连起来
();
以上就是将函数声明变成了表达式,即把函数声明用一对 ()
包裹起来
这就等价于:
var foo = function () {...}; // 这就不是定义,而是表达式了。
foo();
除此之外,转变表达式的办法还是很多的。边学习边补充。