箭头函数为何不能使用 call 或 apply

作者:袖梨 2026-07-16
箭头函数不能使用call或apply改变this指向,因其this是词法继承、定义时即锁定;call/apply的第一个参数被忽略,但其余参数正常传递;它也没有arguments对象,不支持动态上下文操作。

箭头函数不能使用 callapply 改变 this 指向,根本原因在于它压根没有自己的 this 绑定机制。

箭头函数的 this 是词法继承,不是动态绑定

普通函数的 this 在每次调用时才确定,取决于谁调用、怎么调用(比如 obj.fn()this 指向 obj);而箭头函数在定义那一刻,就从外层作用域“抄”来了 this 值,并牢牢锁定——后续任何调用方式都不会影响它。

  • 这个 this 可能是全局对象(如浏览器中的 window),也可能是某个外层函数的 this,甚至 undefined(严格模式或模块顶层)
  • callapply 的设计逻辑是“临时把函数挂到目标对象上再执行”,但箭头函数体内根本没有可被覆盖的 this 存储位置,挂上去也没地方写

call/apply 的第一个参数被忽略

当你写 arrowFn.call({x: 1}, 'a', 'b')arrowFn.apply({x: 1}, ['a', 'b']),传入的 {x: 1} 会被完全无视。函数内部的 this 仍是你写箭头函数时所在环境的那个 this

  • 不会报错,但也不会生效——行为符合规范,不是 bug
  • 第二个参数(实参数组)可以正常传递并接收,只是 this 不受影响

它也不具备 arguments 和动态上下文能力

callapply 常用于借用方法(比如 Array.prototype.slice.call(arguments)),但箭头函数连 arguments 对象都没有,更无法参与这类基于运行时上下文的操作。

  • 想访问参数,必须用 rest 参数:(...args) => {...}
  • 需要借用数组方法?得用普通函数,或改用扩展运算符(如 Math.max(...arr)
  • 需要事件回调里访问实例属性?别用箭头函数,否则 this 指向会出错

bind 同样无效,但参数预绑定仍可用

bind 返回的新函数仍是箭头函数,this 不变;不过它支持参数预置——只是这部分和 this 无关。

  • 例如:const fn = (a, b) => console.log(this.val, a, b); const bound = fn.bind({val: 'no effect'}, 1); bound(2); 输出的是原始 this.val(比如 undefined),不是 'no effect'
  • a 会是 1b 会是 2 —— 参数传递照常工作

相关文章

精彩推荐