zoukankan      html  css  js  c++  java
  • javascript this指针指向?

    前言

    理解javascript的指针就需要先了解js的执行环境和作用域!执行环境的定义了变量或函数有权访问的其他数据,决定了它们各自的行为。每个执行环境都有一个与之关联的变量对象,环境中定义的所有的变量和函数都保存在这个对象中。虽然我们编写的代码无法访问这个对象,但解析器在处理数据时会在后台使用它。

    1、全局执行环境

    全局执行环境是最外围的一个执行环境,根据js实现的宿主环境的不同,表示执行环境的对象也不一样。在web浏览器中认为window就是全局执行的对象。因此所有的全局变量和函数都是作为window对象进行创建的。某个执行环境中的所有代码执行完毕后,该环境被销毁,保存在其中的所有的变量和函数定义也会被销毁。每个函数都有自己的执行环境,当执行流进入一个函数的时候,函数的环境就会被推入一个环境栈中。而在函数执行之后,栈将其环境弹出。

    2、作用域链

    当代码在一个环境中执行时候,会创建变量的一个作用域链(scope chain)。作用域链的用途,是保证对执行环境有权访问的所有的变量和函数的有序访问。作用域链的前端,始终都是当前执行的代码所在的环境的变量对象,如果这个环境是函数,则将其活动对象作为变量对象。活动对象在最开始的时候只包含一个变量,arguments对象。作用域链的下一个对象来自包含(外部)环境,而再下一个对象则来自下一个包含对象,这样一直延续到全局。

    JavaScript由于其在运行期进行绑定的特性,JavaScript 中的 this 可以是全局对象、当前对象或者任意对象,这完全取决于函数的调用方式。JavaScript 中函数的调用有以下几种方式:作为对象方法调用,作为函数调用,作为构造函数调用,和使用 apply 或 call 调用。

    看下面第一个例子

    var point = { 
          x : 0, 
          y : 0, 
         moveTo : function(x, y) { 
                         console.log(this);//1
                         this.x = this.x + x; 
                         this.y = this.y + y; 
                 } 
       };
    point.moveTo(1,1); //this 绑定到当前对象,即point对象
    console.log(point);//2

    第一个位置上的this我们打印的时候发现这里的this指向就是point 这个对象!

    point.moveTo()这个方法执行后就更改了对象point的属性x和y

    第二个例子

    function func(x) { 
           this.x = x;
          console.log(this);

    func(2);

    我们发现这个时候的this指向是window  why?

    这个很好理解,func(2) 可以写成window.func(2);由于任何函数或者全局的属性都是window对象下面的,那么这里的this当然就是window

    第三个例子

    var point = { 
          x : 0, 
          y : 0, 
          moveTo : function(x, y) { 
                          // 内部函数
                         var moveX = function(x) { 
                                              console.log(this);
                                              this.x = x;
                                              }; 
                         // 内部函数
                         var moveY = function(y) { 
                                              this.y = y;
                                               console.log(this);
                                              }; 
                        moveX(x); 
                        console.log(moveX() in point);//false
                        console.log(moveX() in window);//true
                        moveY(y); 
              } 
    }; 
    point.moveTo(1,1); 
    point.x; //=>0 
    point.y; //=>0

    上面的代码我们分析下很好理解!执行point.moveTo(1,1)里面有两个方法,moveX和moveY,这两个方法并没有绑定到对象point上,我们知道所有的方法都是属于window对象的,那么这里的moveX和moveY实际上是window上调用的,并不是属于point对象!

    第四个例子

    function Point(x,y){ 
              console.log(this);//第一次是通过new创建的,返回的是Point{} 它是一个对象,不是单纯的方法了
              this.x = x; // this ?
             this.y = y; // this ?
    }
    var np=new Point(1,1);//所以这里可以理解成这样
    /*
               var np = {
                          x = 1,
                          y =1
                   };
    */
    np.x;//1
    var p=Point(2,2);//这个时候不是通过new创建,就相当于window.Point(2,2),它就绑定到window上了!所以this指向window
    console.log(p);//由于函数Point没有返回值,所以这里的p = undefined
    p.x;//error, p是一个空对象undefined

    总结:

    调用形式
    this指向
    普通函数 全局对象window
    对象的方法 该对象
    构造函数 新构造的对象

    文章参考地址:

    http://www.cnblogs.com/isaboy/ 

    http://www.cnblogs.com/isaboy/archive/2015/10/29/javascript_this.html

  • 相关阅读:
    线程池源码解析
    String与常量池
    spring循环依赖
    ConcurrentHashMap源码解析(JDK8)
    原子类源码分析
    web service和ejb的区别
    RPC
    hashcode()和equals()的区别
    关于json
    Lifecycle of jsf
  • 原文地址:https://www.cnblogs.com/shizhouyu/p/4952615.html
Copyright © 2011-2022 走看看