深入理解JavaScript中的this的完整攻略
什么是this
所谓 this
,就是JavaScript中一个相对特殊的关键字,指向当前函数的执行环境。换句话说,this
可以看做是一个对象,这个对象指向的是函数执行时所在的环境对象,而这个环境对象是由调用方式来决定的。
this指向的典型情况
在JavaScript中,this
的指向是根据如何调用当前函数来确定的,它指向的对象有以下几种情况:
默认绑定
默认绑定是指一个独立的函数直接调用时,this
指向全局对象,即 window
,例如:
function fn() {
console.log(this);
}
fn(); // 输出 window
隐式绑定
隐式绑定就是函数作为某个对象的方法被调用时,this
指向该对象,例如:
var obj = {
name: '张三',
fn: function() {
console.log(this.name);
}
};
obj.fn(); // 输出 '张三'
显示绑定
显示绑定通常使用 call()
、 apply()
和 bind()
方法显式的指定 this
的值,例如:
function fn() {
console.log(this.name);
}
var obj1 = { name: '张三' };
var obj2 = { name: '李四' };
fn.apply(obj1); // 输出 '张三'
fn.call(obj2); // 输出 '李四'
fn.bind(obj1)(); // 输出 '张三'
new绑定
用 new
关键字调用构造函数时,返回一个新的对象,这个新的对象就是 this
指向的对象,例如:
function Person(name) {
this.name = name;
}
var p = new Person('张三');
console.log(p.name); // 输出 '张三'
改变this指向的方法
如果想要改变函数内 this
的指向,有以下几种方法:
使用 call() 方法
使用 call()
方法可以直接调用函数,同时改变 this
的指向,例如:
var obj1 = { name: '张三' };
var obj2 = { name: '李四' };
function fn() {
console.log(this.name);
}
fn.call(obj1); // 输出 '张三'
fn.call(obj2); // 输出 '李四'
使用 apply() 方法
apply()
方法和 call()
方法类似,区别在于参数的传递方式不同,例如:
var obj1 = { name: '张三' };
var obj2 = { name: '李四' };
function fn(arg1, arg2) {
console.log(this.name, arg1, arg2);
}
fn.apply(obj1, [1, 2]); // 输出 '张三', 1, 2
fn.apply(obj2, [3, 4]); // 输出 '李四', 3, 4
使用 bind() 方法
使用 bind()
方法可以绑定函数内 this
指向的对象,并且复制函数,例如:
var obj1 = { name: '张三' };
var obj2 = { name: '李四' };
function fn() {
console.log(this.name);
}
var fn1 = fn.bind(obj1);
var fn2 = fn.bind(obj2);
fn1(); // 输出 '张三'
fn2(); // 输出 '李四'
使用箭头函数
箭头函数的 this
绑定的是它所在的作用域,而不是调用时的作用域,例如:
var obj = { name: '张三' };
var fn = () => {
console.log(this.name);
};
fn.call(obj); // 输出 '张三'
示例
示例1:示范this默认指向全局(浏览器中的window对象)
function Person(name) {
this.name = name;
this.eat = function() {
console.log(this.name + ' 正在吃饭');
}
}
var p = new Person('张三');
var eatFunc = p.eat; // 单独取出 sayName 方法
eatFunc(); // 输出 'undefined 正在吃饭'
在执行 eatFunc()
方法时,this
的指向发生了变化,由 p
对象变成了全局对象 window
,导致在 eat()
方法中使用 this
调用 name
属性时,输出 null
或 undefined
。这种情况可以通过使用 bind()
方法来显式的重新绑定 this
的指向,例如:
var eatFunc = p.eat.bind(p);
eatFunc(); // 输出 '张三 正在吃饭'
示例2:示范解决事件回调函数中this指向问题
var button = document.getElementById('myButton');
button.addEventListener('click', function() {
console.log(this); // 输出 <button id="myButton">点击我</button>
});
在回调函数中使用 this
指向的是当前元素,通过这种方法可以方便地操作当前元素,例如:
var button = document.getElementById('myButton');
button.addEventListener('click', function() {
this.disabled = true;
});
以上就是JavaScript中 this
的详细解释及应用,期望本文对你有所帮助。