「这是我参与2022首次更文挑战的第10天,活动详情查看:2022首次更文挑战」
大家好,我是 摸鱼小公举,真正的强者,不会怨天尤人,如果想不被别人看轻,你就只有付出比别人多十倍百倍的努力,才能站的比别人更高。上一篇文章是 WOW动画的使用 ;今天我们来学习一下改变this指向的多种方法。
关于this简介
this的指向在函数定义的时候是确定不了的,只有函数执行的时候才能确定this到底指向谁,实际上this的最终指向的是那个调用它的对象,以下是this指向的几种情况。
1,在全局中this指的是window对象
console.log(this) // window
2,在函数内部
(1)事件函数 this指的是事件触发者
HTML代码
<button id="test">测试按钮</button>
JS代码
var obj = document.getElementById("test");
obj.onclick = function () {
console.log(this); //<button id="test">测试按钮</button>
};
(2)普通函数 this指的是调用者
function a(){
console.log(this) // window
}
a();
3,当一个函数被call或者apply调用时,this指向传入的对象的值
var obj = {
fn: function(){
console.log(this);
}
}
obj.fn() // fn这个函数
obj.fn.call("that") //that这个字符串
obj.fn.apply("that") //that这个字符串
4,箭头函数中自身没有this,箭头函数中的this要向上查找
function wait() {
setTimeout( () => {
//this指向当前对象
console.log(this) //Window
}, 1000)
}
wait()
5,在Vue中this的指向
data中的this指向window
生命周期函数中的this都指向Vue实例对象
Vue的v-on指令的JS语句,其中的this是window
computed中的this指向Vue实例对象
methods中的this,普通函数的this指向vue实例对象,而普通函数的回调函数的this是window;
改变this指向的方法
call
第一个参数是this指向的新对象,第二个参数开始相当于传参,语法: b.call(a,1,2)
在此给大家分享一个实用方法: 两个对象互相检索是否含有相同的属性
Object.prototype.hasOwnProperty.call( 指向的对象, 包含的属性);此方法我经常用来赋值,比如可以用于Vue中data自定义数据对象与接口数据对象中是否有相同属性,有则赋值。
var obj = { v: 4, f: 6, i: 7 };
var obj2 = { v: 0, t: 6, i: 5 };
Object.keys(obj).forEach(key => {
if (Object.prototype.hasOwnProperty.call(obj2, key)) {
obj[key] = obj2[key];
}
});
console.log(obj) //{v: 0, f: 6, i: 5}
apply
第一个参数是this指向的新对象,第二个参数是以数组的方式,相当于arguments;语法:b.apply(a,[1,2])
function fn(a, b) {
console.log(this.name, a, b);
}
var obj = {
name: "Amy",
fn: function () {
console.log(this.name);
},
};
fn.call(obj, "1", "2"); //Amy 1 2
fn.apply(obj, ["1", "2"]); //Amy 1 2
对比这两种方法其实是差不多都是立即调用,结果是一样的,就是传参的方式不一样而已
bind
bind 与 apply/call 一样都能改变函数this指向,但bind并不会立即执行函数,而是返回一个绑定了this的新函数,你需要再次调用此函数才能达到最终执行。注意多次调用bind无效,按第一次算。
function fn(a,b){
console.log(this.name,a,b)
}
var obj={
name:'Amy',
fn:function(){
console.log(this.name)
}
}
fn.bind(obj,'3','2') () //Amy 3 2
new
构造函数中的this与被创建的新对象绑定,当创建上fn的函数以后, 我们就可以通过 new 关键字调用,也就是通过构造函数来创建对象了。这里是实例化一个对象Zn
function fn(){
this.name="二麻子"
}
var Zn=new fn() //this指向Zn
console.log(Zn.name) //二麻子
return
在构造函数时,使用return返回Object时,当去new一个实例对象时,会将this指向改变为return的Object;
function fn(){
this.name="二麻子"
return {
name:"二流子"
}
}
var Zn=new fn()
console.log(Zn.name) //二流子
结语:
其实此文章没有过多的原理解释,感兴趣的朋友可以自己去研究一下;好了文章到此就结束了,欢迎大家( 点赞+评论+关注 ) 有问题可以来互相交流一下。希望这篇文章对大家有帮助,也希望大家多多支持我,今天是我参与2022首次更文挑战的第10天,加油!