js中的call、apply、bind理解

call、apply


一、作用

每个函数都包含两个方法,call() 和 apply();
在ES5中,this总是指向调用该函数的对象(这里不讨论ES6中的箭头函数this指向问题);
在特定的作用域内调用函数,并且改变该函数的this指向 ;

1.call 

<script>

	console.log(this);  			//window
	
	window.color = 'red';
	document.color = 'blue';
	var color1 = {
		color: 'orange'
	}
	function getColor(){
		consolor.log(this.color);
	}
	getColor();						//'red'
	
	// 以下均是执行 getColor 函数,只不过是改变了this的指向

	getColor.call(); 				//this默认指向window  	'red'
	getColor.call(this); 			//this指向window 		'red'
	getColor.call(window); 			//this指向window  		‘red’
	getColor.call(document); 		//this指向document 		'blue' 
	getColor.call(color1);			//this指向color1 		'orange'
	
	//多个参数情况
	
	var sum = {
		a: 0,
		b: 0,
		getSum: function(c, d){
			return this.a + this.b + c + d;
		}
	}
	var s1 = {
		a : 1,
		b:  2
	}
	sum.getSum.call(s1, 3, 4);		// 10
	
</script>

2. apply

<script>

	function getColor(){
		console.log(this.color);
	}
	window.color = 'red';
	document.color = 'blue';
	var color1 = {
		color: 'orange'
	}
	getColor.apply();
	getColor.apply(this); 			//this指向window 		'red'
	getColor.apply(window); 		//this指向window  		‘red’
	getColor.apply(document); 		//this指向document 		'blue' 
	getColor.apply(color1);			//this指向color1 		'orange'
	
	//多个参数情况
	
	function getColor(color){
		this.color = color;
		this.get = function(){
			console.log(this.color);
		}
	}
	function setColor(color){
		getColor.apply(this, arguments);
	}
	var set = new setColor('orange');
	set.get();						//orange

</script>

二、区别
传递参数不同

call(this, 参数1, 参数2, 参数3, …)
apply(this,[参数1, 参数2, 参数3, …])
call()方法 和 apply()方法 唯一的区别就是传递参数不同,call()方法第一个参数是this,后面的参数必须一个一个的写出来,apply()方法第一个参数是this,后面跟了一个数组,参数都写在这个数组里面。
如果apply()方法后面参数不跟数组会怎么样呢?

会报错: Uncaught TypeError: CreateListFromArrayLike called on non-object

bind


一、作用

绑定函数,改变this指向

  • 我们经常碰到这种情况,创建一个变量保存当前this
  • <script>
    
    	var foo = {
    		name: 'jiangfulai',
    		click: function(){
    			var _this = this;
    			document.body.onclick = function(){
    				console.log(_this.name);
    			}
    		}
    	}
    	foo.click();			//jiangfulai
    	
    </script>
    

    以上写法也可以,但是不够优雅,我们可以通过bind(),更优雅的写出这个代码

  • <script>
    
    	var foo = {
    		name: 'jiangfulai',
    		click: function(){
    			document.body.onclick = function(){
    				console.log(this.name);
    			}.bind(this);
    		}
    	}
    	foo.click();			//jiangfulai
    	
    </script>
    

    二、区别

    bind() 方法 和 call() 方法 、apply() 方法有一定的区别

  • bind() 方法是返回对应的函数,需要自己调用。
  • call() 方法、apply()方法是立即执行
  • 微妙的差距!

    call 、bind 、 apply 这三个函数的第一个参数都是 this 的指向对象,第二个参数差别就来了:
    call的参数是直接放进去的,第二第三第n个参数全都用逗号分隔,直接放到后面 obj.myFun.call(db,‘成都’, … ,‘string’ );
    apply的所有参数都必须放在一个数组里面传进去 obj.myFun.apply(db,[‘成都’, …, ‘string’ ]);
    bind除了返回是函数以外,它 的参数和call 一样。
    当然,三者的参数不限定是string类型,允许是各种类型,包括函数 、 object 等等!

猜你喜欢

转载自blog.csdn.net/AN0692/article/details/105533108