javascript的this关键字详解

 更新时间:2019年05月20日 16:32:04   作者:iceberg_yao  
这篇文章主要介绍了javascript的this关键字的用法,文中通过示例代码介绍的非常详细,对大家的学习或者工作具有一定的参考学习价值,需要的朋友们下面随着小编来一起学习学习吧

this 的定义

表示当前执行代码的环境对象

 因此可将 this 的剖析分为“全局环境” 和 “函数环境” 两种类型的环境对象

全局环境

console.log(this === window); // true
 
var a = 10;
console.log(this.a); // 10

函数环境

在函数内部,this 的取值取决于函数被调用时的运行环境。

这里涉及到内存里的数据结构相关的知识点,当我们定义以下字面量对象时会发生一系列的关联关系

var obj = { name: 'Tom' };

javascript 引擎会先在内存中生成 { name: 'Tom' } 对象,接着再把这个对象的内存地址赋值给 obj 变量,所以 obj 变量保存的只是一个内存地址而已,如果要获取 obj.name,javascript 引擎会先从 obj 变量中拿到内存地址,然后从该地址中获取原始对象,再返回 name 属性。

而属性值为函数时,该函数会被保存在内存中,然后将该内存地址赋值给该属性,因此该地址赋值给不同环境执行时它的作用域是不一样的,而 this 对象就是指向函数当前的执行环境对象,执行环境是会在 Event Loop(事件循环)过程中变化的,因此 this 在函数环境下是属于运行时的。

var name = 'Tom';
 
var obj = {
  name: 'Iceberg',
  say: function() {
    console.log('my name is ' + this.name);
  },
  sub: {
    say: function() {
      console.log('my name is ' + this.name);
    }
  }
};
 
obj.say(); // my name is Iceberg
obj.sub.say() // my name is undefined;
 
var say = obj.say;
say(); // my name is Tom;

上面的例子说明 obj.say() 执行环境为 obj 对象,而 obj.sub.say() 的执行环境却是 obj.sub 对象,而对于 obj.sub 来说并没有 name 属性,因此为 undefined;而 var say = obj.say; 则表示将 say 方法的内存地址赋值给全局变量,因此从全局变量 name 中取值。

运用场景

接下来从 this 在函数环境下的不同运用场景来剖析

事件回调函数

var handler = {
	nickname: 'anonymous',
	register: function() {
	  console.log(this.nickname);
	}	
}
 
$('#registerBtn').on('click', handler.register); // undefined

以上逻辑点击触发后输出的是 undefined,因为函数被当做事件触发的回调函数执行时,this 是指向该触发事件对应的元素,如要 this 仍然以 handler 对象为执行环境,则可使用函数的 bind 方法进行执行环境对象的绑定操作。

$('#registerBtn').on('click', handler.register.bind(handler)); // anonymous

在 react 中经常需要在回调函数中调用 this.state、this.props,按照上面的分析,将当前环境对象 bind 到回调函数中即可。

如果是使用的箭头函数定义回调函数即可无需 bind,因为箭头函数中 this 就是对应定义时所在的对象。
 构造函数

要理解 this 在构造函数中的逻辑就要理清楚构造函数在实例化过程中都发生了什么。

function A() {
  this.name = 'Tom';
  this.age = 20;
}
var a = new A();

使用 new 命令实例化构造函数 A 的过程中会发生以下流程

  1. 创建一个空对象,作为将要返回的对象实例
  2. 将该空对象的原型指向构造函数的 prototype 属性
  3. 将该空对象赋值给构造函数内部的 this 关键字
  4. 执行构造函数内部代码
  5. 默认返回 this 对象(如 return 的为非对象类型,如数字 123,会被忽略进而默认 return this 对象)
  6. 由以上逻辑可知道 this 关键字在构造函数中表示的是其实例对象。

bind

bind 方法将函数体中的 this 指向新对象并返回一个新函数

function A() {
  this.nickname = 'Tom';
  this.say = function() {
    console.log(this.nickname);
  }
}
var b = { nickname: 'John' };
var a = new A();
var say = a.say;
var say1 = a.say.bind(a);
var say2 = a.say.bind(b);
say(); // undefined
say1(); // Tom
say2(); // John

call & apply

call 方法是指 Function.prototype.call,因此每个函数都会具备 call 方法,fun.call(thisArg, arg1, arg2, ...),call 方法接收的第一个参数会替换原有的 this 指向的执行环境对象。

function A() {
  this.name = 'Tom';
  this.sayName = function(){
    console.log(this.name);
  };
}
 
function B() {
  this.name = 'John';
}
 
var a = new A();
a.sayName.call(new B()); // John

而 apply 方法与 call 的区别仅在于 call 接收参数列表而 apply 接收数组参数或者类数组对象(如函数的 arguments 对象)。

总结

由于 javascript 的 Event Loop 原理,决定了执行上下文会不断变化,因此 this 对象诞生于表达当前的执行环境对象。

以上所述是小编给大家介绍的javascript的this关键字的用法详解整合,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对脚本之家网站的支持!

相关文章

  • 80%应聘者都不及格的JS面试题

    80%应聘者都不及格的JS面试题

    超过80%的候选人对下面这道JS面试题的回答情况连及格都达不到。这究竟是怎样神奇的一道JS面试题?他考察了候选人的哪些能力?对正在读本文的你有什么启示?
    2017-03-03
  • ES6中数组array新增方法实例总结

    ES6中数组array新增方法实例总结

    这篇文章主要介绍了ES6中数组array新增方法,结合实例形式总结分析了ES6中数组array各种新增方法的功能及使用技巧,需要的朋友可以参考下
    2017-11-11
  • 超级详细的webpack Plugin讲解

    超级详细的webpack Plugin讲解

    plugin是插件的意思,通常是用于对某个现有的架构进行扩展,下面这篇文章主要给大家介绍了关于webpack Plugin的相关资料,文中通过示例代码介绍的非常详细,需要的朋友可以参考下
    2022-04-04
  • JS截取字符串常用方法详细整理

    JS截取字符串常用方法详细整理

    截取字符串的使用比较广泛,有很多中方法,本文粗略的整理了一些,感兴趣的额朋友可以才参考下
    2013-10-10
  • js选项卡的制作方法

    js选项卡的制作方法

    这篇文章主要为大家详细介绍了js选项卡的制作方法,具有一定的参考价值,感兴趣的小伙伴们可以参考一下
    2017-01-01
  • CSS代码格式化和压缩的方法与技巧

    CSS代码格式化和压缩的方法与技巧

    下面脚本之家编辑就将一些css的格式化与压缩技巧简单的介绍下,一把情况需要尽量的缩写样式,减少体积,然后用工具进行压缩,然后再测试网页。
    2007-06-06
  • JavaScript简单获取页面图片原始尺寸的方法

    JavaScript简单获取页面图片原始尺寸的方法

    这篇文章主要介绍了JavaScript简单获取页面图片原始尺寸的方法,可通过Image()对象直接获取图片的原始宽高,简单实用,需要的朋友可以参考下
    2016-06-06
  • 一句话JavaScript表单验证代码

    一句话JavaScript表单验证代码

    纯属技术交流,在实际应用中不建议那么做。建议js加载比较好。
    2009-08-08
  • js实现复选框的全选和取消全选效果

    js实现复选框的全选和取消全选效果

    在很多网站都有这样的功能,当点击一个全选按钮之后,所有的复选框都会被选中,再点击之后会取消全选,功能非常的人性化,可以省却很多人力,本文将简单介绍一下JS如何实现此功能
    2017-01-01
  • JS实现商品倒计时实现代码

    JS实现商品倒计时实现代码

    JS实现商品倒计时实现代码,需要的朋友可以参考一下
    2013-05-05

最新评论