JavaScript 上下文切换

 JavaScript是一门非常灵活的语言,它和其他编程语言相比有很多独特的地方。其中一个较为突出的表现就是,在JavaScript中允许我们手动更改上下文 。这会方便我们进行状态的共享,尤其是在事件回调中显得意义重大。但这也市场给一些初学者带来费解和疑惑。下面我们为大家讲述几种较为常用的手动更改上下文的方法:

function  Student(name) {

        this.name = name;

        this.clicked =function () {

           console.log(this.name);

       }

        this.introduce = function () {

            document.onclick = this.clicked;

        }

     }

      var s1 = new Student("jack");

扫描二维码关注公众号,回复: 1922783 查看本文章

      s1.introduce();

上面的例子是一个简单的上下文发生更改的案例,  我们的预期效果是点击文档的时候,打印出jack 的名字 。但是由于绑定事件时,上下文发生了更改,所以当我们点击文档的时候打印出来的值是undefined ,所以我们需要手动变换一下上下文;

解决方案:

1.     变量赋值传递

var self = this;

 this.clicked =function () {

    console.log(self.name);

}

 this.introduce = function () {

     document.onclick =this.clicked;

 }

这种方法是应用最为广泛的一种方法,在上下文发生更改之前使用变量将其缓存下来,在执行的时候利用缓存对象调用到属性值。

2.     使用bind方法

实际上JavaScript的运营商已经为我考虑到了上下文切换的问题 ,并在es5中新加了bind方法,专门用来更改函数的作用域 。

       this.clicked =function () {

          console.log(this.name);

      }

       this.introduce = function () {

           document.onclick = this.clicked.bind(this);

       }

上述代码中,我们利用bind方法 进行了作用域的更改,实际上是将内部代码的执行对象更改为了外部的this 对象 。

3.    使用代理函数 。

function Student(name) {

 this.name = name;

 this.proxy=function (func,thisObject) {

             return (function () {

                 returnfunc.apply(thisObject,arguments);

             });

       }

       this.clicked =function () {

          console.log(this.name);

      }

       this.introduce = function () {

           document.onclick = this.proxy(this.clicked,this);

       }

    }

 var s1 = new Student("jack");

     s1.introduce();

对比发现上边的代码格式发生了比较大的变化 ,这里比较关键的是我们定义了一个proxy的函数,这个函数实际上是模拟了jquery中的$.proxy 方法,原理是利用aplly方法进行作用域的更改,不过我们将这部分的逻辑封装成一个函数,这样看上去会更加清爽一些。当然我们也可以直接使用apply或call方法,实现执行对象的更改 。

4.   apply 或call 方法

这里简单介绍一下apply方法和call方法   。这两个方法在功能上有些类似,最基本的用法是 b.apply(a,arguments) 或 b.call(a,arguments[0], arguments[1], arguments[2]…)  . 上述功能是将b方法的功能复制给a对象 。它们的调用对象都是函数 ,不同点是后续传入的参数个数。apply 只需要传入arguments 数组,arguments代表函数所有参数,call 方法需要依次传入函数的参数 。

注意:直接使用call或apply方法并不能妥善的解决上下文切换的问题, 我们最好的做法是像type3所介绍的方法一样结合一个代理函数去使用它们 。下面并不是一个很好地示例,因为我们结合了type1 的方法,不过通过这个案例你依然能看出apply或call方法 在处理上下文切换方面的作用 。

this.introduce = function () {

           var self = this;

           document.onclick=function () {

                return (function () {

                    console.log(this.name);

                }).apply(self,arguments);

           }

   }

     

  

          

猜你喜欢

转载自blog.csdn.net/tuohai_/article/details/72847341
今日推荐