您好,欢迎来电子发烧友网! ,新用户?[免费注册]

您的位置:电子发烧友网 > 源码下载 > java源码下载 >

JAVA中关于this和that的一些知识

大小:0.3 MB 人气: 2017-09-25 需要积分:1

  新手在入门 Java 的过程中,一定会踩很多关于 this 的坑,出现问题的本质就是 this 指针的指向和自己想的不一样。笔者在入门学习的过程中,也踩了很多坑,于是便写下本篇文章记录自己“踩坑”历程。

  一。 this 在哪里?

  在上篇《从 Java 作用域说开去》分析中,我们知道,在 ExecuTIon Context 中有一个属性是 this,这里的 this 就是我们所说的 this 。this 与上下文中可执行代码的类型有直接关系,this 的值在进入执行上下文时确定,并且在执行上下文运行期间永久不变。

  this 到底取何值?this 的取值是动态的,是在函数真正被调用执行的时候确定的,函数定义的时候确定不了。因为 this 的取值是执行上下文环境的一部分,每次调用函数,都会产生一个新的执行上下文环境。

  所以 this 的作用就是用来指明执行上下文是在哪个上下文中被触发的对象。令人迷惑的地方就在这里,同一个函数,当在不同的上下文进行调用的时候,this 的值就可能会不同。也就是说,this 的值就是函数调用表达式(也就是函数被调用的方式)的 caller。

  二。 this & that 具体指的是谁?

  目前接触的有以下14种情况,笔者打算一一列举出来,以后如果遇到了更多的情况,还会继续增加。

  既然 this 是执行上下文确定的,那么从执行上下文的种类进行分类,可以分为3种:

  

  那么接下来我们就从 Global ExecuTIon Context 全局执行上下文,FuncTIon ExecuTIon Context 函数执行上下文,Eval Execution Context Eval执行上下文 这三类,具体谈谈 this 究竟指的是谁。

  (一)。 全局执行上下文1. 非严格模式下的函数调用

  这是函数的最通常用法,属于全局性调用,因此 this 就代表全局对象 Global。

  var name = ‘halfrost’;function test() { console.log(this); // window console.log(this.name); // halfrost}test();

  在全局上下文(Global Context)中,this 总是 global object,在浏览器中就是 window 对象。

  2. 严格模式下的函数调用

  严格模式由 ECMA 5.1引进,用来限制 Java 的一些异常处理,提供更好的安全性和更强壮的错误检查机制。使用严格模式,只需要将 ‘use strict’ 置于函数体的顶部。这样就可以将上下文环境中的 this 转为 undefined。这样执行上下文环境不再是全局对象,与非严格模式刚好相反。

  在严格模式下,情况并不是仅仅是 undefined 这么简单,有可能严格模式夹杂着非严格模式。

  先看严格模式的情况:

  ‘use strict’;function test() { console.log(this); //undefined};test();

  上面的这个情况比较好理解,还有一种情况也是严格模式下的:

  function execute() { ‘use strict’; // 开启严格模式 function test() { // 内部函数也是严格模式 console.log(this); // undefined } // 在严格模式下调用 test() // this 在 test() 下是 undefined test(); // undefined } execute();

  如果严格模式在外层,那么在执行作用域内部声明的函数,它会继承严格模式。

  接下来就看看严格模式和非严格模式混合的情况。

  function nonStrict() { // 非严格模式 console.log(this); // window } function strict() { ‘use strict’; // 严格模式 console.log(this); // undefined }

  这种情况就比较简单了,各个模式下分别判断就可以了。

  (二)。函数执行上下文3. 函数调用

  当通过正常的方式调用一个函数的时候,this 的值就会被设置为 global object(浏览器中的 window 对象)。

  严格模式和非严格模式的情况和上述全局执行上下文的情况一致,严格模式对应的 undefined ,非严格模式对应的 window 这里就不再赘述了。

  4. 方法作为对象的属性被调用

  var person = { name: “halfrost”, func: function () { console.log(this + “:” + this.name); }};person.func(); // halfrost

  在这个例子里面的 this 调用的是函数的调用者 person,所以会输出 person.name 。

  当然如果函数的调用者是一个全局对象的话,那么这里的 this 指向又会发生变化。

  var name = “YDZ”;var person = { name: “halfrost”, func: function () { console.log(this + “:” + this.name); }};temp = person.func;temp(); // YDZ

  在上面这个例子里面,由于函数被赋值到了另一个变量中,并没有作为 person 的一个属性被调用,那么 this 的值就是 window。

  上述现象其实可以描述为,“从一个类中提取方式时丢失了 this 对象”。针对这个现象可以再举一个例子:

  var counter = { count: 0, inc: function() { this.count ++; }}var func = counter.inc;func();counter.count; // 输出0,会发现func函数根本不起作用

  这里我们虽然把 counter.inc 函数提取出来了,但是函数里面的 this 变成了全局对象了,所以 func() 函数执行的结果是 window.count++。然而 window.count 根本不存在,且值是 undefined,对 undefined 操作,得到的结果只能是 NaN。

非常好我支持^.^

(0) 0%

不好我反对

(0) 0%

      发表评论

      用户评论
      评价:好评中评差评

      发表评论,获取积分! 请遵守相关规定!