this指向取决于函数调用方式而非定义方式:1. 普通调用时非严格模式指向window、严格模式为undefined;2. 对象方法调用(obj.fn())指向该对象;3. call/apply/bind可显式绑定this,bind绑定不可覆盖;4. 箭头函数无this,继承外层词法作用域。

“this” 绑定是 JavaScript 面试高频考点,出错往往不是因为不会,而是没理清执行上下文和调用方式的对应关系。核心就一点:this 指向谁,取决于函数怎么被调用,而不是怎么被定义。
普通函数调用:this 默认指向全局或 undefined
在非严格模式下,独立调用函数(如 fn()),this 指向全局对象(浏览器中是 window);严格模式下则为 undefined。这是最容易踩的坑——尤其当函数从对象方法中提取出来单独使用时。
- 避免直接赋值后调用:
const handler = obj.method; handler();→ this 丢失 - 修复方式:用箭头函数(继承外层 this)、bind 显式绑定、或调用时用 call/apply
- 现代写法推荐:类中用箭头函数声明回调,或在 constructor 中 bind
对象方法调用:this 指向调用它的那个对象
只要函数是作为对象属性被“点出来”调用的(obj.method()),this 就指向该对象。但要注意嵌套对象和中间变量的影响。
-
const obj = { name: 'a', fn() { console.log(this.name); } }; obj.fn();→ 输出 'a' -
const o = obj; o.fn();→ 依然输出 'a',因为调用时左侧仍是 obj(引用不变) - 但
const { fn } = obj; fn();就变成普通调用,this 丢失
call / apply / bind:手动控制 this 指向
这三个方法本质都是显式绑定 this,区别在于执行时机和参数传入方式:
-
fn.call(obj, a, b):立即执行,参数逐个传 -
fn.apply(obj, [a, b]):立即执行,参数用数组传 -
const bound = fn.bind(obj, a); bound(b);:返回新函数,可延迟执行,预设部分参数 - bind 生成的函数无法再被 call/apply 覆盖 this(硬绑定优先级最高)
箭头函数:没有自己的 this,继承外层词法作用域
箭头函数不创建执行上下文,它内部的 this 始终等于定义时所在作用域的 this,且不可被 call/bind 改变。
- 适合用在回调、事件处理器、定时器中,避免 this 丢失
- 不能用作构造函数(没有 prototype),也不能使用 arguments
- 注意:外层如果是普通函数,其 this 仍需按规则判断,箭头函数只是“转发”它
搞懂这四类场景,再配合几个典型例子手写推演,面试时基本稳了。关键不是死记,而是每次看到函数调用,下意识问一句:“它是怎么被调用的?”











