箭头函数的限制与用法
箭头函数与 bind 的区别在哪?
fn.bind(this): 造出一个新的「绑定版本」, 仍是普通函数, 只是 this 被永久固定;=>: 不创建任何绑定, 函数根本没有 this, 查找方式与查普通变量一样沿词法环境向外找;- 结论: bind 是运行时的替换且多一层包装, 箭头函数是定义时的捕获且零开销;
箭头函数为什么没有 arguments?
- 事实: 箭头函数没有自己的
arguments, 访问到的总是外层函数的那个; - 用途: 需要把当前 this 与 arguments 一起透传出去时, 能少写两个中间变量;
function defer(f, ms) {
return function () {
setTimeout(() => f.apply(this, arguments), ms); // 取自外层包装器
};
}
- 对照: 不用箭头函数就要先存
const ctx = this, args = [...arguments], 再在setTimeout的普通函数里使用;
箭头函数有哪些硬性限制?
- 没有
this、没有arguments、没有super; - 不能当构造函数: 构造需要把 this 绑定到新对象, 箭头函数没有 this, 用
new调用直接抛错;
const f = () => {};
new f(); // TypeError: f is not a constructor
- 不适合做对象方法: 它取不到「调用它的那个对象」, 得到的永远是外层 this;
什么时候该用箭头函数?
- 判断标准: 这个函数是否应该跟着外部的 this 走;
- 适合:
forEach、setTimeout、Promise 等由外部调用的短回调, 希望在当前上下文中执行;
const group = {
title: "Our Group",
students: ["John"],
showList() {
this.students.forEach((s) => console.log(this.title + ": " + s)); // this = group
},
};
group.showList(); // "Our Group: John"
- 不适合: 对象方法、构造函数、需要转发调用者
arguments的包装函数; - 对照: 把回调换成
function (s) {},forEach默认不传 this, 会得到this === undefined;