判断函数this指向的关键是看调用形式:1. new调用优先级最高,this指向新实例;2. 其次为call/apply/bind显式绑定;3. 再次为对象方法调用(点号左侧对象);4. 默认绑定(非严格模式为window/global,严格模式为undefined);5. 箭头函数无this,继承外层普通函数的this。

判断函数的 this 指向,关键不是背规则,而是看“谁在调用它”以及“怎么调用”。只要盯住调用形式,按优先级逐层检查,几秒钟就能确定。
先看有没有 new 调用
这是最高优先级。只要函数前面加了 new,this 一定指向新创建的实例对象,其他所有绑定方式都会被忽略。
-
new Person()→this是新Person实例 - 即使用了
bind或call,new也会覆盖它们 - 注意:箭头函数不能被
new调用,会报错
再看有没有 call、apply 或 bind
显式绑定次之。如果函数被 fn.call(obj)、fn.apply(obj) 或 fn.bind(obj) 调用,this 就是传进去的第一个参数(obj)。
-
fn.call({x:1})→this是{x:1} -
bind返回的新函数,this已固化,后续再用call也无法改 - 但
new绑定仍能覆盖bind的结果
接着看是不是对象方法调用
也就是形如 obj.method() 这种写法。此时 this 指向“点号左边最近的那个对象”。
-
user.profile.getInfo()→this是profile,不是user - 一旦脱离点调用,比如
const fn = obj.method; fn(),就退回到默认绑定 - 解构、传入回调(如
setTimeout(obj.fn, 100))、数组取值都会导致隐式绑定丢失
最后看是否独立调用
既没 new、也没显式绑定、也没点号调用,就是默认绑定——这是兜底规则。
- 非严格模式下:
this是window(浏览器)或global(Node) - 严格模式下:
this是undefined - ES6 模块顶层代码自动启用严格模式,所以
this总是undefined
特别留意箭头函数
它不参与以上四条规则,没有自己的 this。它的 this 在定义时就固定下来,等于外层第一个普通函数的 this 值。
- 写在全局:继承全局上下文的
this(通常是window或undefined) - 写在普通函数内:和该函数的
this一致 - 无法用
call/apply/bind改变











