ES6 新增加了箭头函数的语法,如果你还不知道什么叫箭头函数表达式,请戳这里查看 关于箭头函数的描述
概括来说
借用MDN的话:箭头函数表达式的语法比函数表达式更简洁,并且没有自己的this
,arguments
,super
或new.target
等,也不能用作构造函数。
箭头函数表达式更适用于那些本来需要匿名函数的地方。
仔细地看
1. this
(执行上下文)的指向区别
普通函数中的this
:
-
在简单调用中,非严格模式下指向
window
对象;
严格模式下为undefined
。function normal() { console.log(this); // => window {...} } normal(); // ------------------ 'use strict'; function strictNormal() { console.log(this); // => undefined } strictNormal();
-
作为某个对象方法调用时,
this
指向该对象。var obj = { normal: function() { console.log(this); // => { normal: f() } } } obj.normal();
-
被间接调用时,指向
call/apply/bind
的第一个参数;
若第一个参数为null
,this
的指向参考第一条的规则。function normal() { console.log(this); // => { name: 'Object' } } var obj = { name: 'Object' } normal.call(obj);
-
普通函数被用作构造函数,用
new
关键字构造实例时,this
指向新建的实例。function Normal() { console.log(this); // => Normal {} } var normal = new Normal();
箭头函数中的this
:
- 没有自己的
this
,内部this
值以为与外部非箭头函数的this
。
☆ 由于箭头函数的this
由外部非箭头函数的this
决定,因此,若需要将一个函数作为回调函数去执行,并且不希望函数中的this
发生改变,这时用箭头函数最适合不过。如果是普通函数,则需要用bind()
进行this
绑定。
class Contruct {
constructor (name) {
this.consName = name;
}
arrowLog = () => {
console.log(this.consName);
}
normalLog () {
console.log(this.consName);
}
}
const construct = new Contruct('arrow');
setTimeout(construct.arrowLog, 1000); // 1s后 => 'arrow'
setTimeout(construct.normalLog, 1000); // 1s后 => 'undefined'
setTimeout(construct.normalLog.bind(construct), 1000); // 1s后 => 'arrow'
2. 是否可作为构造函数使用的区别
普通函数: 可以作为构造函数来使用,用new
去新建对象实例。
箭头函数: 不能作为构造函数,会报错。
那么,问题来了 ↓。
为什么箭头函数不能用作构造函数?
箭头函数本身是存在原型链的,它也有自己的构造函数,但原型链到箭头函数这一环就断了,因为它没有 prototype 属性,没办法连接它的实例的原型链,所以箭头函数就无法作为构造函数。
3. arguments 对象
普通函数: 普通函数内部,arguments
为特殊的类数组对象。包含了函数被调用时的参数列表。
箭头函数: 箭头函数内部是没有arguments
对象,依赖于外部非箭头函数。
如果箭头函数想要拿到全部参数,也可以通过 剩余参数语法 获取到全部参数。
const arrow = (...arg) => {
console.log(arg); // => [1, [1, 2], [1, 2, 3]]
}
arrow(1, [1, 2], [1, 2, 3]);