有几种定义函数的方式
How many ways to define a function
一句话:五种 —— 函数声明、函数表达式、箭头函数、Function 构造器、以及对象/类里的方法简写。
但面试真正想听的是它们的差别, 尤其是前三种:
| 提升 | this | arguments | 能否 new | |
|---|---|---|---|---|
| 函数声明 | 整体提升,声明前可调用 | 调用时决定 | 有 | 能 |
| 函数表达式 | 只提升变量名 | 调用时决定 | 有 | 能 |
| 箭头函数 | 只提升变量名 | 定义时的外层 this | 没有 | 不能 |
箭头函数不是「更短的 function」—— 它没有自己的 this、 没有 arguments、 不能当构造器、没有 prototype。 所以对象方法里想用this 指向该对象,就不能用箭头函数。
会追问:「Function 构造器为什么不用?」—— 它接收字符串当函数体,相当于 eval: 有注入风险、拿不到闭包、 而且引擎没法优化。知道它存在但说明不该用就是正确答案。
In one line: five — function declaration, function expression, arrow function, the Function constructor, and method shorthand inside an object or class.
But what the interview actually wants is the differences, especially between the first three:
| Hoisting | this | arguments | Can you new it | |
|---|---|---|---|---|
| Function declaration | Hoisted whole, callable before its line | Decided at call time | Yes | Yes |
| Function expression | Only the variable name is hoisted | Decided at call time | Yes | Yes |
| Arrow function | Only the variable name is hoisted | The enclosing this where it was written | No | No |
An arrow function is not “a shorter function” — it has no this of its own, no arguments, cannot be a constructor, and has no prototype. So if an object method needs this to be that object, it cannot be an arrow function.
Follow-up: “Why does nobody use the Function constructor?” — it takes the body as a string, which makes it eval in disguise: an injection risk, no access to the surrounding closure, and nothing the engine can optimise. Knowing it exists and saying it should not be used is the right answer.