this指向

一、this指向在函数定义的时候是确定不了的,只有在函数执行时才能确定this到底指向谁,实际上this最终指向的是最后调用它的对象。

1.demo1
``

function a(){
var user="shark Jan";
console.log(this.user);
console.log(this);
}
a();

 


``
##window是js中的全局对象,在以上例子中,函数a是被window调用的,所以this指向了window.
由于window没有user这个变量,所以this.user打印的结果是undefined;
但是由于this指向了window,所以this的打印结果是window.

2.demo2
``

var o={
user:"shark Jan",
fn:function(){
console.log(this.user); //shark Jan
}
}
o.fn();

 


``
这个例子中,由于fn函数是被o对象调用的,所以fn中的this指向了o对象。所以打印结果是"shark Jan";

3.
demo3
``

var o={
user:"shark Jan",
fn:function(){ 
console.log(this.user); //undefined
}
}
window.o.fn();

 


``
##看了上面的例子,按照上面的理论,我们很容易会想到打印undefined;因为window作为全局对象调用了fn,this应该指向window,但是window中并没有user这个属性,所以会返回undefined.
但是这里并非如此,打印结果是"shark Jan"
为了搞清楚这个问题我们再看一个实例
demo4
``

var o={
a:10,
b: {
a: 12,
fn: function () {
console.log(this.a); //12
}
}
};
o.b.fn();

 


``
这个例子中fn同样是o调用的,但是this并没有指向o,它打印的结果是12.
这是为什么呢?
##a.如果一个函数中有this,但是它没有被上一级对象调用,那么this指向的就是window(这里暂时不探讨严格版js)。
##b.如果一个函数中有this,同时又被上一级对象调用,那么this指向的是上一级对象。
##如果一个函数中有this,同时又包括多个对象,那么尽管函数是被最外层对象调用,this仍然会指向上一层调用它的对象。
这里插一点,对象不能隔代调用。比如
demo5
``

``
在这里由于o与c之间间隔一个对象b,所以无法打印this指向。

4.还有一种情况比较特殊,例如
demo6
``

var o={
a:10,
b:{
a:12,
fn:function(){
console.log(this.a); //undefined
console.log(this); //window
}
}
}
var j=o.b.fn;
j();
j();

 


``
看了上面的实例,你想出的结果可能是12,12,因为这里this应该指向的是上一级对象b呀。
但是事实并非如此,你还没有理解一句话,this永远指向的是最后调用它的对象,也就是在函数执行时,是谁调用的?
这里var j=o.b.fn,实际上只是定义了j变量,并没有执行j,所以this指向无法判断,但是后面的j(),执行了j变量,也就调用了fn(),但是这里执行j()的其实是window,所以this实际上指向了window.
window中并没有a属性,所以this.a指向了undefined,this指向window.

二、构造函数中的this指向
demo
``

function Fn(){
this.user="shark Jan"
}
var a= new Fn();
console.log(a.user); //shark Jan

 


``
上面实例中a可以点出Fn里的user,是因为new关键字可以改变this指向。
这里的new创造了一个构造函数,构造函数的作用就是初始化对象,又使用变量a创建了一个Fn的实例,就相当于复制了一份Fn到对象里,这里的this就指向里新创建出来的a.

三、当this碰到return时,
``

demo1
function fn(){
this.user="shark Jan";
return function(){};
}
var a= new fn;
console.log(a.user); //undefined

demo2
function fn(){
this.user="shark Jan";
return {};
}
var a= new fn;
console.log(a.user); //undefined

demo3
function fn(){
this.user="shark Jan";
return 1;
}
var a= new fn;
console.log(a.user); //"shark Jan"

 


``

##通过以上实例可以发现,当返回值是一个对象时,this指向的就是那个返回值的对象,但是当返回值不是一个对象时,那么this仍然指向函数的实例。

##补充说明:
1.在事件中,this指向触发事件的对象,但是比较特殊的是,在IE中attachEvent中的this总是指向全局对象window。

2.严格版javascript中,默认的this不再指向window,而是指向undefined.

3.new操作符的作用
demo
``

function fn(){
this.num=1;
}
var a= new fn();
console.log(a.num); //1

 

总结:

1.this永远指向函数运行时所在的对象,而不是函数创建时所在的对象,不再任何对象内的this或者匿名函数的this,指向window.

2.如果是call,apply,with,它们指定的this是谁,就是谁。

3.普通函数调用中的this,函数被谁调用指的就是谁。

 

 

 



这里this为什么会指向a,因为new关键字会创建一个空对象,然后回自动调用一个apply方法,将this指向这个空对象a,这样的话,函数内部的this就会被这个空对象a代替。







posted @ 2017-08-28 09:59  鲨鱼余烁  阅读(125)  评论(0编辑  收藏  举报