【生意多】-免费发布分类信息
当前位置: 首页 » 新闻 » 教程 » 正文

彻底搞懂 JS 中 this 机制

放大字体  缩小字体 发布日期:2020-04-28 08:30:18    浏览次数:24
导读

  。如果仅通过this的英文解释,太容易产生误导了。它实际是在函数被调用时才发生的绑定,也就是说this具体指向什么,取决于你是怎么调用的函数。  因为foo()是直接调用的(独立函数调用),没有应用其他的绑定规则,这里进行了默认绑定,将全局对象绑定this上,所以this.a 就解析成了全局变量中的a,即2。  注意:在

  。如果仅通过this的英文解释,太容易产生误导了。它实际是在函数被调用时才发生的绑定,也就是说this具体指向什么,取决于你是怎么调用的函数。

  因为foo()是直接调用的(独立函数调用),没有应用其他的绑定规则,这里进行了默认绑定,将全局对象绑定this上,所以this.a 就解析成了全局变量中的a,即2。

  注意:在严格模式下(strict mode),全局对象将无法使用默认绑定,即执行会报undefined的错误

  除了直接对函数进行调用外,有些情况是,函数的调用是在某个对象上触发的,即调用位置上存在上下文对象。

  所以这里对foo的调用存在上下文对象obj,this进行了隐式绑定,即this绑定到了obj上,所以this.a被解析成了obj.a,即3。

  这里调用链不只一层,存在obj1、obj2两个对象,那么隐式绑定具体会绑哪个对象。这里原则是获取最后一层调用的上下文对象,即obj1,所以结果显然是4(obj1.a)。

  为什么会这样,obj.foo 赋值给bar,那调用bar()为什么没有触发隐式绑定,使用的是默认绑定呢。

  这里有个概念要理解清楚,obj.foo 是引用属性,赋值给bar的实际上就是foo函数(即:bar指向foo本身)。

  那么,实际的调用关系是:通过bar找到foo函数,进行调用。整个调用过程并没有obj的参数,所以是默认绑定,全局属性a。

  同样的道理,虽然参传是obj.foo,因为是引用关系,所以传参实际上传的就是foo对象本身的引用。对于setTimeout的调用,还是 setTimeout - 获取参数中foo的引用参数 - 执行 foo 函数,中间没有obj的参与。这里依旧进行的是默认绑定。

  相对隐式绑定,this值在调用过程中会动态变化,可是我们就想绑定指定的对象,这时就用到了显示绑定。

  显示绑定主要是通过改变对象的prototype关联对象,这里不展开讲。具体使用上,可以通过这两个方法call(...)或apply(...)来实现(大多数函数及自己创建的函数默认都提供这两个方法)。

  这里因为显示的申明了要绑定的对象,所以this就被绑定到了obj上,打印的结果自然就是obj1.a 和obj2.a。

  js中的new操作符,和其他语言中(如JAVA)的new机制是不一样的。js中,它就是一个普通函数调用,只是被new修饰了而已。

  数是否在new中调用(new绑定)?如果是的话this绑定的是新创建的对象。 数是否通过call、apply(显式绑定)或者硬绑定调用?如果是的话,this绑定的是 指定的对象。 数是否在某个上下文对象中调用(隐式绑定)?如果是的话,this绑定的是那个上下文对象。 果都不是的话,使用默认绑定。如果在严格模式下,就绑定到undefined,否则绑定到 全局对象。 var bar = foo()

  这种情况主要是用在不关心this的具体绑定对象(用来忽略this),而传入null实际上会进行默认绑定,导致函数中可能会使用到全局变量,与预期不符。

  所以对于要忽略this的情况,可以传入一个空对象ø,该对象通过Object.create(null)创建。这里不用{}的原因是,ø是真正意义上的空对象,它不创建Object.prototype委托,{}和普通对象一样,有原型链委托关系。

  最后,介绍一下ES6中的箭头函数。通过“=”而不是function创建的函数,叫做箭头函数。它的this绑定取决于外层(函数或全局)作用域。

  通过上面两个列子,我们看到箭头函数的this绑定font color=red只取决于外层(函数或全局)的作用域/font,对于前面的4种绑定规则是不会生效的。它也是作为this机制的一种替换,解决之前this绑定过程各种规则带来的复杂性。

  通过上面两个列子,我们看到箭头函数的this绑定font color=red只取决于外层(函数或全局)的作用域/font,对于前面的4种绑定规则是不会生效的。它也是作为this机制的一种替换,解决之前this绑定过程各种规则带来的复杂性。

  我们在使用js的过程中,对于this的理解往往觉得比较困难,再调试过程中有时也会出现一些不符合预期的现象。很多时候,我们都是通过一些变通的方式(如:使用具体对象替换this)来规避的问题。可问题一直存在那儿,我们没有真正的去理解和解决它。

  本文主要参考了《你不知道的Javascript(上卷)》,对this到底是什么,具体怎么绑定的,有什么例外情况以及ES6中的一个优化方向,来彻底搞清楚我们一直使用的this到底是怎么玩的。

 
关键词: js this
(文/小编)
打赏
免责声明
• 
本文为小编原创作品,作者: 小编。欢迎转载,转载请注明原文出处:http://www.31duo.com/news/show-182579.html 。本文仅代表作者个人观点,本站未对其内容进行核实,请读者仅做参考,如若文中涉及有违公德、触犯法律的内容,一经发现,立即删除,作者需自行承担相应责任。涉及到版权或其他问题,请及时联系我们。
 

(c)2016-2019 31DUO.COM All Rights Reserved浙ICP备19001410号-4

浙ICP备19001410号-4