你不知道的 this 原理

大家好,我是十七,大家对 this 一定很熟悉吧, 那你知道为什么会有 this 机制嘛? 今天来说道说道~

var a = "a"
var obj = {
    a : "obj.a",
    fn : function () {
        console.log(this.a)
    }
}
var newFn = obj.fn

newFn()  // a
obj.fn()  // obj.a

明明是同样的函数,为什么执行结果会不一样呢?

我想你会说 this 指向不一样, 那么 this 指向为什么会不一样呢? 这就是今天讨论的重点哦!

对于 this 呢,我的理解就是当前函数执行的环境, 里面存放着许许多多的声明变量和方法。

这其实和 JavaScript 语言底层的数据存储方式有关,在JavaScript 中,字符串、数字 都是用原始值保存, 对象 、数组、函数都是用索引值来保存,这就是说当你声明一个函数,

你拿到这个函数只是拿到了他的引用值,而不是拿到了它本身。请看

 var fn1 = function(){
     console.log(a)
 }
 var fn2 = fn1
 fn1.toString = function(){
     console.log("tostring")
 }
 fn2.toString() // tostring

fn1修改 tostring 方法之后, fn2 也同样被修改。

回到上面 obj.fn() 的代码,也就是说,当你调用 obj.a 时,js 会首先找到 obj 这个对象的索引值, 然后再根据 fn属性,找到fn函数的索引值,然后再执行这个函数,

也就是说这个函数执行的时候,是 通过obj.fn 的索引值执行的, 那么自然 obj 就是 obj.fn 的执行环境,即 fn 的 this 是 obj。

如果在全局执行 fn ,那么就是 window 通过索引值找到的 fn ,那么这个函数执行的环境就是window,所以 this 指向的是 window。

打个比方啊,window 相当于公司董事长,obj 相当于部门主管,fn 就是一个普通的职工。就如董事长想做一件事,告诉了部门主管要做什么事,部门主管呢 就找到了员工,让员工去做相应工作,这时候员工做事按照谁的规则走呢,当然是主管了,因为是主管派给你的任务,这就和 obj 调用 fn 一样,fn 必须按照 obj 的环境来执行。在 window 环境执行相当于董事长直接找你来工作,那你的工作当然要按照董事长的要求来走,相当于在全局调用 fn,fn 的 this 指向当然是 window。

this 机制这样设计的原因呢我是这样理解的:

    官方希望能够提供一种机制,可以让相同的函数在不同的环境执行能够满足不同的需求,假如每个函数只能对一个环境使用,那么在多个环境你就需要重复写很多的函数,代码会变得非常繁琐。如果能够改变函数其内部的环境指向,那就可以实现函数的复用,极大提升开发体验。

以上是我的理解,有不对的地方还请大家多多指教。

猜你喜欢

转载自blog.csdn.net/zjk325698/article/details/112982121