this指向问题
现在有一个对象 和全局变量 name,age
var name = 'lihua'
var age = 20;
var obj = {
name: '小米',
age: 10,
getname: function() {
return function() {
console.log(this.name, this.age)
}
}
}
当我把对象里的getname方法 重新赋值给另一个变量的时候 然后调用的时候它会输出什么?
var fn = obj.getname()
fn()
它输出了全局里面的name 和 age很明显我们需求是要输出对象里的name 和age 这个时候this指向发生了改变
这时候有同学就要说了 你这不是画蛇添足吗? 把返回的匿名函数删掉不就好了吗
我tm跟你讲知识点 你在这投机取巧?
这个时候我们就可以使用js提供的改变this指向的api了
第一种,call()
function.call(thisArg, arg1, arg2, …)
thisArg
可选的。在 function 函数运行时使用的 this 值。请注意,this可能不是该方法看到的实际值:如果这个函数处于非严格模式下,则指定为 null 或 undefined 时会自动替换为指向全局对象,原始值会被包装。
arg1, arg2, …
指定的参数列表。
var name = 'lihua'
var age = 20;
var obj = {
name: '小米',
age: 10,
getname: function() {
return function() {
console.log(this.name, this.age)
}
}
}
var fn = obj.getname()
fn.call(obj) //改变this指向
这个时候就变成了对象里的name 和 age
第二种bind()
function.bind(thisArg[, arg1[, arg2[, …]]])
thisArg
调用绑定函数时作为 this 参数传递给目标函数的值。 如果使用new运算符构造绑定函数,则忽略该值。当使用 bind 在 setTimeout 中创建一个函数(作为回调提供)时,作为 thisArg 传递的任何原始值都将转换为 object。如果 bind 函数的参数列表为空,或者thisArg是null或undefined,执行作用域的 this 将被视为新函数的 thisArg。
arg1, arg2, …
当目标函数被调用时,被预置入绑定函数的参数列表中的参数。
返回值
返回一个原函数的拷贝,并拥有指定的 this 值和初始参数。
var name = 'lihua'
var age = 20;
var obj = {
name: '小米',
age: 10,
getname: function() {
return function() {
console.log(this.name, this.age)
}
}
}
var fn = obj.getname()
fn.bind(obj) //这个地方返回的是复制的obj指向的一个函数体
这个时候我们打印却发现没有任何东西
这是因为这个api返回的是它复制的方法 所以要有结果需要执行一次
把最后一行加上执行符号
fn.bind(obj)()
这个时候就有了
这个返回回来的函数体 不执行 可以用变量存起来 多次调用
还有一种apply()
apply() 方法调用一个具有给定this值的函数,以及作为一个数组(或类似数组对象)提供的参数。
注意:call()方法的作用和 apply() 方法类似,区别就是call()方法接受的是参数列表,而apply()方法接受的是一个参数数组。
//例
call(this,1,2,3,4)
apply(this,[1,2,3,4,5])
我们用这个api一样可以改变this指向
var name = 'lihua'
var age = 20;
var obj = {
name: '小米',
age: 10,
getname: function() {
return function() {
console.log(this.name, this.age)
}
}
}
var fn = obj.getname()
fn.apply(obj)