JS中this总结

82 阅读2分钟

认识this

在JavaScript中,this是一个比较灵活的关键字,他表示当前调用对象。this是函数体内自带的一个对象指针,它能够始终指向调用对象。当函数被调用时,使用this可以访问调用对象。

为什么需要this

由于函数可以在不同的运行环境执行,所以需要有一种机制,能够在函数体内部获得当前的运行环境(context)。所以,this就出现了,它的设计目的就是在函数体内部,指代函数当前的运行环境。

    var a = 66   //被函数fn访问
        var obj = {
            a: 1,
            fn: function () {
                console.log(a)  //打印66
            }
        }
        obj.fn()

        var obj2 = {
            a: 1, //被函数fm访问
            fm: function () {
                this.b=1
                console.log(this.a) //打印1
            }
        }
        obj2.fm()  //同时给obj2添加成员b

小结

从上面代码知道,当运行obj.fn() 时,是访问不到obj成员a,打印了全局变量a。为了能够访问到obj2a成员,JavaScript就为我们提供了this,使得this.a能够访问obj2的成员a,同时能够添加或更新成员。

绑定规则

  • 默认绑定:非严格模式下this指向全局对象window, 严格模式下this会绑定到undefined
        "use strict";
        var fn = function () {
            return this
        }
        console.log(fn()) //undefined
  • 隐式绑定:对象以成员的方式调用函数时, 如 obj.foo()的调用方式, foo内的this指向obj
        var obj = {
            a: 1,
            fn: function () {
                return this
            }
        }
        console.log(obj.fn())  //返回obj对象
  • 显示绑定:apply,call,bind调用模式下,this指向第一个参数,如foo.call(obj)
        var obj={
            name:'蜗牛',
            getName:function(){
                console.log(this.name)
            }
        }
        var otherObj={
            name:'导弹'
        }
        var name='回想'
        obj.getName()//蜗牛
        obj.getName.call();//回想
        obj.getName.call(otherObj);//导弹
        obj.getName.apply();//回想
        obj.getName.apply(otherObj);//导弹
        obj.getName.bind(this)();//回想
        obj.getName.bind(otherObj)();//导弹
  • new绑定 :使用new来调用一个函数,会构造一个新对象并把这个新对象绑定到调用函数中的this。
        function fn() {
            this.a = 1
            this.b = 2
        }
        var obj = new fn()
        console.log(obj) //打印对象{a:1,b:2}
  • 箭头函数绑定:this的指向由外层作用域决定的。
        //声明位置
        var fn = (()=>{
            console.log(this.a)
        })  
        var a=66
        var obj={
            a:1,
            fn:fn
        }
        //调用位置
        obj.fn();//66
        //调用位置
        fn();//66

根据函数的调用方式的不同,this 会指向不同的对象

  • 以函数的形式(包括普通函数、定时器函数、立即执行函数)调用时,this 的指向永远都是 window。比如fun();相当于window.fun();
  • 以方法的形式调用时,this 指向调用方法的那个对象
  • 以构造函数的形式调用时,this 指向实例对象
  • 以事件绑定函数的形式调用时,this 指向绑定事件的对象
  • 使用 call 和 apply 调用时,this 指向指定的那个对象