首页 > js的this 指向问题:为什么点击按钮执行函数内部创建的函数this指向的事window?

js的this 指向问题:为什么点击按钮执行函数内部创建的函数this指向的事window?

this一直有点晕,今天写了一个测试,但是还是不理解,求高手给个通俗易懂的简答:
以下代码,为什么点击按钮执行函数内部创建的函数this指向的事window?

(function(){
            console.log(self);
            console.log(this);//这里的this指向window
        })();

    
<body>
<button id="di" >ssss</button>
<script type="text/javascript">
var d=document.getElementById('di');
    function a(){
        name='111'
        console.log(this);
    }

    d.addEventListener('click',function(){
        a();//a打印的this是window
        console.log(this);//打印的是d对应的button元素
        var self=this;、//保存this
        //为什么内部创建的函数this指向window
        (function(){
            console.log(self);
            console.log(this);//这里的this指向window
        })();
    });
</script>
</body>
</html>

d.addEventListener('click',function(){
    a();//a打印的this是window
    你这么调用a不就相当于window.a(),this肯定是window啊
    console.log(this);//打印的是d对应的button元素
    这个this和当前dom元素绑定的处理函数有关,应该是addEventListener方法绑定事件的时候给callback函数的this绑定d元素吧。这个你可以查查资料是不是。
    
    var self=this;//保存this
    //为什么内部创建的函数this指向window
    (function(){
        console.log(self);
        这里self是你这个匿名函数的父作用域的self,就是父作用域的this,和上一句一样。
        console.log(this);//这里的this指向window
        
        这个匿名函数不就和a函数一样吗?
        换种写法:
        
        function test(){
            console.log(this);
        }
        test() === window.test();
    })();
});

在闭包中使用 this 对象也可能会导致一些问题。我们知道, this 对象是在运行时基于函数的执行环境绑定的:在全局函数中, this 等于 window,而当函数被作为某个对象的方法调用时, this 等于那个对象。不过,匿名函数的执行环境具有全局性,因此其 this 对象通常指向 window。但有时候由于编写闭包的方式不同,这一点可能不会那么明显。 --摘自JavasSript高级程序设计

从上面的话我个人理解分出三种情况。

  1. 全局函数调用,this指向window

  2. 匿名函数调用,this指向window

  3. 函数作为某个属性对象调用,此时this指向那个对象。例如执行a.func(); 此时this指向a。如果是a.b.func()。此时this指向a.b。

其实我个人觉得还有一种情况就是局部函数被调用。例如

function outer(){
    function inner(){
        console.log(this);
    }
    inner();
}
outer();// this 指向windows

此时this也是指向 windows。

你这里是属于 匿名函数调用所以this指向window。 至于为什么你的click回调函数this指向Button我个人理解这里是属于约定吧。
以上是我个人理解,欢迎各位大神指正我呀。


js中,匿名函数的this指向全局作用域


简单点说this是指向函数的调用者,foo.bar()这样的,this就是foo
bar()的话,就没有调用者,this就会指向window


任何地方以:

function a() {
    console.log(this);
}

的形式定义函数,此函数都会被加到顶级对象中(浏览器中是 window
匿名函数也是如此。

至于为什么有个 this 指向对应的元素,是因为 addEventListener 就是这样实现的。自己也可以实现,参考文档 func.apply()func.call()func.bind()


我理解的 Javascript中this的含义是:调用包含this的函数的那个对象,
第一种情况,全局对象window调用的函数中的this

alert(this)//window

function fooCoder(x) {
    this.x = x;
}
fooCoder(2);
alert(x);// 全局变量x值为2

第二种情况,构造函数中的this(之前见过许多次)

function Person(name){  
     this.name = name;  
};  

var tom = new Person("tom");

这里的this 指向的是通过构造函数 new 出来的那个tom对象。因为tom调用了 this所在的Person函数。

第四种情况,对象的方法中调用的this

Person.prototype.say = function (){  
     console.log(this.name +" say hello~");  
}  

这里的this 指向的是调用这个方法的对象。例如tom.say(),这时this指向的是tom。原理同上
这种是在全局作用域中调用了包含了this的那个alert函数,所以这时this是指全局作用域,即window。

对于浏览器的三种添加事件监听的方式this也有不同。
第一种:直接在标签内写 onclick=“fn”
第二种:在js中 onclick=fn
第三种:在js中 用el.attachEvent或者el.addEventListener()

三种方式添加的事件处理函数运行的scope是不同的,不同浏览器也不尽相同。
IE

js: el.onclick = fn ,fn的this->el
在标签中 onclick = "fn()" ,fn的this->window
js: el.attachEvent('onclick',fn); ,fn的this->window

Firefox、Chrome、Opera

js: el.onclick = fn ,fn的this->el
在标签中 onclick = "fn()" ,fn的this->window
js: el.addEventListener('onclick',fn); ,fn的this->el

我之前也纠结过这个问题,后来查找犀牛书才发现其实很好判断。
1.当函数作为函数(包括匿名函数)调用时,在严格模式下,this为undefined,非严格模式下,this统统指向window
2.当函数作为方法调用时,this指向调用它的那个对象
3.在call、applay用法中,this指向设定的上下文


因为function a的定义在全局,它的作用域链直接就是globle,所以this是指向window的呀.

【热门文章】
【热门文章】