最近被问到一个问题:
javaScript 中的箭头函数 ( => ) 和普通函数 ( function ) 有什么区别?
我当时第一反应是:这很简单啊,不就是一种简化的写法吗,还依稀记得对this
指向有影响。好吧,记不清楚了,然后迅速开始百度之旅~~
箭头函数
引入箭头函数有两个方面的作用:更简短的函数并且没有定义this
绑定。
基础语法:
(arg1, arg2, ..., argn) => {函数声明};
不绑定this
在箭头函数出现之前,每个新定义的函数都有它自己的this值。箭头函数不会创建自己的this,它只会从自己的作用域链的上一层继承this,总是指向函数定义生效时所在的对象。
// 1. `Person()`构造函数定义 this 作为它自己实例,而`add()`函数定义 this 作为全局对象。
function Person() {
this.age = 10;
foo: setInterval(function add() {
this.age ++;
console.log(this.age);
}, 100);
}
new Person().foo;
// 2. 通过将this值分配给封闭的变量,可以解决this问题。
function Person() {
let _this = this;
_this.age = 10;
foo: setInterval(function add() {
_this.age ++;
console.log(this.age);
}, 100);
}
new Person().foo;
// 3. this正确指向person对象
function Person() {
this.age = 10;
foo: setInterval(() => {
this.age ++;
console.log(this.age);
}, 1000);
}
new Person().foo;
不能作为构造函数
let Person = () => {};
let person = new Person();
console.log(person); // TypeError: Foo is not a constructor
不绑定arguments
// 箭头函数内部的变量arguments,其实是函数foo的arguments变量。
function foo() {
setTimeout(() => {
console.log(arguments);
}, 100);
}
foo(1, 2, 3) // ['1': 1, '2': 2, '3': 3]
//
function foo() {
let f = (...args) => args[0];
return f(2);
}
foo(1); // 2
没有prototype属性
let Person = () => {};
console.log(Person.prototype); // undefined
解析顺序
箭头函数中的箭头不是运算符,但箭头函数具有与常规函数不同的特殊运算符优先级解析规则。
let foo;
foo = foo || function() {}; // ok
foo = foo || () => {}; // SyntaxError: invalid arrow-function arguments
foo = foo || (() => {}); // ok