function (someArgs) { someStatements }
function name(someArgs) { someStatements }
(someArgs) => { someStatements }
function
引导的函数表达式。g(); // 报错,函数还没有声明
f(); // 报错,函数还没有声明
let f = function g() { console.log('Hi'); } // =后边的是一个具名函数表达式
f(); // 'Hi'
g(); // 报错,具名函数表达式的名字只能在函数体内部调用
具名函数表达式在语法上,多一个名字:
name
属性就是该名字,不会因为因为赋值而改变;let g = function f(n) { }
let h = g
g.name // 'f'
h.name // 'f'
(function(){}).name // '',空字符串,没有名字
let k = function () {}
k.name // 'k'
let factorial = function fac (n) {
if (n <= 1) return 1;
else return n * fac(n - 1); // 不要使用 factorial(n - 1)
}
factorial(4) // 24
fac(4) // 报错
let factorial = function fac (n) {
if (n <= 1) return 1;
else return n * factorial(n - 1);
}
factorial(4) // 24
let f = factorial;
factorial = 1;
f(4) // 报错
箭头函数表达式的语法更加简洁,含义上有一些差异,用法上也有一些限制:
this
;arguments
对象;new
调用会 报错,无法访问 new.target
关键字);yield
,不能用以创建生成器。()
可以省略;{}
可以省略,返回值就是该语句/表达式的值。{}
包围。/* 函数体只有一个语句 */
() => 单个语句
单个参数 => 单个语句
(单个参数) => 单个语句
(参数1, 参数2) => 单个语句
let f = ()=>console.log(111)
f() === undefined // true
/* 函数体有多个语句,使用{} */
() => { 多个语句 }
单个参数 => { 多个语句 }
(单个参数) => { 多个语句 }
(参数1, 参数2) => { 多个语句 }
let g = ()=>{}
()
;let f = ()=>{ a:1 } // 不报错,a被当成一个标签,执行了表达式 “1”,返回 undefined
let f = ()=>{ a: 1, b: 2 } // 报错
let f = ()=>{ a: 1; b: 2 } // 不报错,a,b都时标签
let f = ()=>( {a:1, b:2} ) // 不报错,()改变了优先级
this
的指向。更多因此导致的注意事项,见此