this详解 包括apply call bind 构造函数 继承

 
			//注:(以下this均是ES5非严格模式下的教程)很多朋友对this不是很理解,无非以下几种情况:

			//① 默认情况下this指向window,函数的一般调用方式如foo();
			function foo1() {
				console.log(this); // window
				this.bar1(); // 等价于bar1();
			}

			function bar1() {
				console.log(this); //window
			}
			foo1();
			//②回调函数内部的this指向window
			setTimeout(function() {
				console.error(this);
			}, 10);
			//③作为对象属性函数内部的指向
			var person1 = {
				name: '小明',
				play: function() { //对象的play属性指代的函数的引用地址
					console.log(this);
					console.log(this.name);
				}
			}
			setTimeout('person1.play()', 1000) //指向小明
			setTimeout(function() {
				person1.play() //指向小明
			}, 1000)
			person1.play(); //this指向person1,  this.name==小明
			var _play = person1.play; //这句话的意思是将函数的引用地址赋值给一个全局变量
			_play(); //window   this.name==null
			//由此可见this和函数声明的位置没有任何关系,只取决于函数的调用方式,谁调用函数,this就指向谁
			//④  call apply第一个参数可以改变函数内部this的指向
			function foo2(num) {
				console.log("foo2:" + num);
				this.count++;
			}
			foo2.count = 0;
			var i;
			for(i = 0; i < 10; i++) {
				if(i > 5) {
					foo2.call(foo2, i);
				}
			}
			console.log(foo2.count); //6,7,8,9  (如果不用foo2.call 那么foo2.count还是0,因为this默认指向window);
			//⑤ bind 也能改变this指向
			function foo3() {
				console.log(this)
			}
			var _foo3 = {
				name: '小红'
			}
			var _foo_3 = foo3.bind(_foo3); //foo3.call(obj)会直接执行函数了。
			_foo_3(); //this会执行对象_foo3

			//⑥ 原生forEach方法会改变函数内部默认this

			[1, 2, 3].forEach(foo3, _foo3); //foo3里面的this指向了_foo3对象

			//补充
			foo3.call(null); //this指向window

			console.log(Object.create(null)) //创建一个空对象,没有任何属性包括property
			foo3.call(Object.create(null)) //foo3 this指向的是空对象; 更安全,传入null的话可能会是里面的this修改全局变量。危险
			function xz() {
				console.log(this)
			}
			var p = {
				ww: 3,
				xz: xz
			}
			var p2 = {
				ww: 5
			}
			var p3 = {
				ww: 7
			}
			p.xz(); // p
			(p2.xz = p.xz)() //window
			p3.xz = p.xz;
			p3.xz() //p3

			//⑦  new 构造函数   里面this指向实例化对象

			function SFN(name) {
				this.name = name;
			}
			SFN.prototype.play = function() {
				console.log(this); //指向对象sFn
			}
			var sFn = new SFN('小兰');
			console.log(sFn.name)
			sFn.play();
			//⑧立即执行函数this指向window
			(function i(){
				console.log("i:",this)
			})()
			
			


下面引入《你不知道的js》里面一段话:


评论
添加红包

请填写红包祝福语或标题

红包个数最小为10个

红包金额最低5元

当前余额3.43前往充值 >
需支付:10.00
成就一亿技术人!
领取后你会自动成为博主和红包主的粉丝 规则
hope_wisdom
发出的红包
实付
使用余额支付
点击重新获取
扫码支付
钱包余额 0

抵扣说明:

1.余额是钱包充值的虚拟货币,按照1:1的比例进行支付金额的抵扣。
2.余额无法直接购买下载,可以购买VIP、付费专栏及课程。

余额充值