JS的this指向深入

this指向深入

this的绑定规则

  • 默认绑定
  • this默认指向了window
  1. 全局环境下this指向了window
  2. 函数独立调用,函数内部的this也指向了window
<script>
function fn(){
	console.log(this);
}
fn();
</script>
  1. 函数被嵌套的函数独立调用时,this默认指向了window
  2. 函数当做对象的方法来调用时,this指向了obj
<script>
var obj = {
	a:2,
	foo:function(){
		var that = this;
		function test(){
			console.log(that.a);
		}
		test();
	}
}
obj.foo();
</script>
  1. 自执行函数内容this也指向了window
<script>
var a = 10;
function foo(){
	(function(){console.log(this.a);}());
}
var obj = {
	a:2,
	foo:foo
}
obj.foo();
</script>
  1. 闭包this默认指向window
<script>
var a = 0;
var obj = {
	a:2,
	foo:function(){
		var c = this.a;
		return function test(){
			console.log(this); 
			return c;
		}
	}
}
var fn = obj.foo();
console.log(fn);
</script>

隐式绑定

<script>
function foo(){
	console.log(this.a);
}
var obj = {
	a:1,
	foo:foo
}
//foo()函数的直接对象是obj,this的指向直接对象。
obj.foo();
</script>

隐式丢失

隐式丢失是指被隐式绑定的函数丢失了绑定对象 从而默认绑定到window
这种情况比较容易出错却非常常见。

<script>

var a = 0;
function foo(){
	console.log(this.a);
}
var obj = {
	a:1,
	foo:foo
	var bar = obj.foo();
	bar();
</script>

把obj.foo()赋值给别名bar,造成隐式丢失的情况,因为只有把obj.foo()赋值了bar变量
而bar与obj对象毫无关系。

new绑定

如果是new关键字来执行函数,相当于构造函数来实例化对象,name内部的this指向了当前实例化的对象

<script>
function fn(){
	console.log(this);
}
var fn = new fn();
console.log(fn);
</script>

使用return关键字来返回对象的时候,this还是指向了当前的对象。

<script>
function fn2(){
	console.log(this);
	return {
		name:'xxx'
	}
}
var fn2 = new fn2();
console.log(fn2);
</script>

严格模式下的this

严格模式下,独立调用的函数内部的this指向了undefined

<script>
function fn(){
	'use strict';
	console.log(this);
}
fn();
//函数apply()和call()
//严格模式下,函数apply()和call()内部的this始终是它们的第一个参数。
var color = 'red';
function showColor(){
	'use strict';
	console.log(this);
	console.log(this.color);
}
showColor.call(undefined);
</script>

this总结

  1. 默认绑定
  2. 隐式绑定
  3. 显示绑定
  4. new绑定
    分别对应了函数的四种调用方式,
    四种调用方式对应了this绑定
    调用方式
  5. 独立调用
  6. 方法调用
  7. 间接调用
  8. 构造方法调用
  • 独立调用 对应 默认绑定
  • 方法调用this指向obj
  • 间接调用通过call()、apply()、bind() 来更改内部的this指向。
  • 构造函数在函数中添加了new关键字,内部中的this会发生改变,它会改变当前的实例化对象。
原文地址:https://www.cnblogs.com/pythonliuwei/p/13528117.html