啊,万恶的this
发布日期:2022-02-08 04:21:00
浏览次数:3
分类:技术文章
本文共 4916 字,大约阅读时间需要 16 分钟。
一、全局下,this一般都指向window
全局下,ES5非严格模式,下面的this都是window。
console.log(this);function abc(){ console.log(this);}abc();
二、对象中的this
1、最常见的this情况:
var a=100;var obj={ a:1, b:function(){ console.log(this);//这个this是当前对象 // 谁调用b方法,this就是谁 }, // this是当前对象外的this指向,这里应该是window c:this.a}var obj1 = obj;obj = { };obj1.b();//浅复制而已,引用没变2、如果在对象的属性对象中:
var a=1000;var obj = { a: 1, b: { c: this.a, //运行到此时obj还没生成,this还是指向window 创建时 还没生成 d: function () { console.log(this); //函数被调用的时候才会执行这句话,同样,谁调用指向谁 } }}console.log(obj);obj.b.d();3、如果obj已经创建完,再给obj增加属性,那么此时的obj.b的this还是指向window。
var a=2000;var obj={ a:1}console.log(obj); obj.b={ c:this.a, d:function(){ console.log(this); }}console.log(obj);4、如果是对象中的属性函数下又新建对象,this指向外层对象obj。
var obj = { a: 1, b: function () { // this var obj2 = { // this指当前对象外this的指向,这里的this指向是obj c: this.a } console.log(obj2.c); }}obj.b();
三、回调函数中的this
回调:函数在另一个函数的参数里,然后被调用,就叫回调。
1、一般的回调函数:(this被重定向到window)
function ab(fn) { fn();}function cd() { // this指向window console.log(this);}ab(cd);2、对象中的回调:(this被重定向到window)
var obj = { a: function (fn) { fn(); }, b: function () { // 如果直接执行obj.b() 这里的this应该是obj对象 // 如果通过上面a方法回调执行当前b的时候,this被重定向到window console.log(this); }}obj.a(obj.b);3、事件是特殊的回调函数,事件回调函数中的this都是被侦听的对象:
document.addEventListener("click", clickHandler);function clickHandler(e) { console.log(this); // this===e.currentTarget}4、把函数写在方法中(匿名的回调函数),this都重定向到window:(不论这个方法放在哪)
var obj = { a: function () { setTimeout(function () { console.log(this)//window }, 100); // 所有的函数一旦被写在一个方法中,这个函数就是匿名的回调函数,在该函数中this指向window setInterval(function () { console.log(this); }, 100) var arr = [1, 2, 3]; arr.map(function () { console.log(this);//window // forEach,filter,reduce,some,every,flatMap }); new Promise(function (resolve, reject) { console.log(this);//window }) }} obj.a();new Promise(function (resolve, reject) { console.log(this);//window})
四、事件函数中的this
事件函数是特殊的回调函数,使用时不会被重定向到window,而是侦听对象;因为太特殊了,单独拿出来再了解了解。
事件侦听的回调函数,this被重新处理,this指向被侦听的对象。(1)最常用的看上面。
(2)放到其他地方也一样。比如放到对象里:var obj={ a:function(){ document.addEventListener("click",this.b); this.b(); }, b:function(e){ // 因为b函数是事件侦听的回调函数,因此这里this指向事件侦听的对象,也就是document console.log(this); console.log(e);//侦听到的事件 }}obj.a();
五、ES6类中的this
一般都是指向当前实例对象,但是静态属性、静态方法都可以指向当前类。
但是要注意:对于面向对象语言来说,一般在静态属性和方法中是不允许使用this这个概念的。class Box{ // 在外面定义,ES7后才有的// 这里的内容是constructor执行后才赋的值//其实在这儿定义的,跟在constructor里定义差不多b=333;a=this.b;static b=444;static a=this.b;//一旦被设为静态属性,this指向都会被设置为当前的类名Boxconstructor(){ // this指向当前实例对象 console.log(this); console.log(this.a,Box.a); this.b=111; this.a=this.b; Box.b=222; //也是静态属性 Box.a=Box.b; console.log(this.a,Box.a);}play(){ // 这里的this都是实例化的对象 console.log(this.a,Box.a); console.log(this);}static run(){ console.log(this); // 因为使用static定义的方法,this指向为当前类名 // 对于面向对象语言来说,一般在静态属性和方法中不允许使用this这个概念}}var a=new Box();a.play();class Ball extends Box{ constructor(){ super();}}var b=new Ball();Ball.run(); // 继承后静态方法也会被继承
六、ES5中类的this
除了静态属性、方法的this指向这个类,其他情况下this一般都指向当前实例化对象。
// 构造函数function Box(){ this.play(); // 构造函数中this,指向new出的实例对象}// 静态的属性、方法,类似于ES6里的静态方法、静态属性定义Box.a=function(){ console.log(this); // this -->Box}Box.b=3;// 写在原型下的属性、方法Box.prototype.play=function(){ console.log(this); // this 就是当前调用该方法的实例对象}Box.prototype.c=10; // 静态属性、方法,this指向类console.log(Box.b);Box.a();var box=new Box(); console.log(box); //与paly中打印的一样// box对象没有play这个对象属性,因此就去原型链中找到最近的play方法,执行这个play方法是由box这个对象执行// 静态属性、方法只和类有关系,与实例化的对象没有任何关系,所以不在box对象中显示。console.dir(Box); //console.dir()可以显示一个对象的所有属性和方法
七、ES6箭头函数中的this
所有箭头函数内的this,都是当前函数外层的this指向。
var fn=()=>{ };var obj={ a:()=>{ console.log(this);//this--->window }, b:function(){ console.log(this);//this--->当前调用方 }, // c跟b的一样 c(){ console.log(this);//this--->当前调用方 }}var obj1=obj;obj1.a();obj1.b();obj1.c();
var obj={ a:function(){ setTimeout(()=>{ // 因为本来是回调函数,this统一都会被执行window; // 但是使用了箭头函数,就会全部把这里this重定向到setTimeout外层,也就是obj。 console.log(this); },100) setTimeout(function(){ console.log(this); // 没有使用箭头函数,this指向window },100); }}obj.a();
八、call、apply、bind
当使用时,都会将函数中this的指向重新指向到对应的对象。
总结
那么总结一下,都有哪些this:
全局下的this、对象中的this、回调函数中的this(事件函数中的this)、ES6类中的this、ES5中类的this、ES6箭头函数中的this、call,apply,bind中的this。最后,其实理解了,this也就善良了。
转载地址:https://blog.csdn.net/weixin_43297321/article/details/104387188 如侵犯您的版权,请留言回复原文章的地址,我们会给您删除此文章,给您带来不便请您谅解!
发表评论
最新留言
哈哈,博客排版真的漂亮呢~
[***.90.31.176]2024年03月26日 13时34分55秒
关于作者
喝酒易醉,品茶养心,人生如梦,品茶悟道,何以解忧?唯有杜康!
-- 愿君每日到此一游!
推荐文章
思科 Packet Tracer 实验六 RIP路由协议基本配置
2019-04-26
计算机网络实验七:DHCP基本配置
2019-04-26
计算机网络实验八:思科NAT的基本配置
2019-04-26
三郎数据结构算法学习笔记:单向环形链表约瑟夫问题
2019-04-26
前端特效H5+css+js:动态可拉进度条+附完整源码
2019-04-26
三郎数据结构学习笔记:双向循环链表(判断是否对称)附源码
2019-04-26
三郎数据结构算法学习笔记:基数排序
2019-04-26
三郎数据结构算法学习笔记:斐波那契(黄金分割法)查找算法
2019-04-26
Java中标识符的命名规则是什么?硬性要求和非硬性要求
2019-04-26
Java中八种基本数据类型的大小,以及他们的封装类
2019-04-26
Spring依赖注入的方式有几种,各是什么?
2019-04-26
SpringMVC怎么样设定重定向和转发的?
2019-04-26
SpringMVC常用的注解有哪些?
2019-04-26
spring bean的生命周期
2019-04-26
计算机网络子网划分详解
2019-04-26
计算机网络生成树算法STP简介
2019-04-26
三郎数据结构算法学习笔记:哈希表查找
2019-04-26
三郎数据结构算法学习笔记:二叉树的三种遍历及增删改查
2019-04-26
三郎数据结构算法学习笔记:顺序存储二叉树
2019-04-26
三郎数据结构算法学习笔记:线索二叉树
2019-04-26