1.
function fn(){
let user = "youyou";
console.log(this.user);
}
fn();//此时的this指向的是window的对象(非严格模式下)
等价于如下:
window.fn(); //指向调用对象window
***********************************************************
2.
var my ={
user: 'youyou',
fn: funciton(){
console.log(this.user); //'youyou'
},
otherFn: {
user: 'nanpan',
fn1: function(){
console.log(this.user); //'nanpan'
}
}
};
my.fn(); // 此时的this的指向就是调用 fn 的对象my(调用时决定)
my.otherFn.fn1(); // 此时的this的指向就是调用 fn1的对象otherFn(调用时决定)
/*特殊情况*/
//此时others的值就是fn1属性对应的值function(){console.log(this.user);},others此时就是一个普通函数,指向window
let others = my.otherFn.fn1;
等价于如下:
others=function(){
console.log(this.user); // 此时的this指向window
}
others(); //'undefined'
***********************************************************
3.
function fn(){
this.user = 'youyou';
}
var a = new fn(); // 此时的new fn()构造了一个对象,赋值给a
typeof a;//"object"
a; //fn{user: "youyou"}
a.user; //'youyou'
function fn(){
this.user = 'youyou';
return 1;//或者是 return undefined
}
var a = new fn(); // 此时的new fn()执行完后,还是构造了一个对象
typeof a;//"object"
a; //fn{user: "youyou"}
a.user; //'youyou'
/*特例return null*/
function fn(){
this.user = 'youyou';
return null;
}
var a = new fn(); // 此时的new fn()执行完后,还是构造了一个对象(虽然null是一个对象)
typeof a;//"object"
a; //fn{user: "youyou"}
a.user; //'youyou'
function fn(){
this.user = 'youyou';
return {};
}
var a = new fn(); // 此时的new fn()执行完后,返回了一个空对象赋值给a
typeof a;//"object"
a; //{}
a.user; //'undefined'
function fn(){
this.user = 'youyou';
return function(){};
}
var a = new fn(); // 此时的new fn()执行完后,返回了一个匿名函数赋值给a
typeof a;//"function"
a; //function(){}
a.user; //'undefined'
总结:如果返回值是一个对象,那么this指向的就是那个返回的对象,如果返回值不是一个对象那么this还是指向函数的实例;
普通函数:this的指向是在调用时确定的,指向的是调用的那个对象
箭头函数的this指向问题:函数体内的this
对象,就是定义时所在的对象,而不是使用时所在的对象
箭头函数导致this
总是指向函数定义生效时所在的对象
function foo() {
setTimeout(() => {
console.log('id:', this.id);
}, 100);
}
var id = 21;
foo.call({ id: 42 });
// 打印出 id: 42
//此时箭头函数this指向就是timer对象(所以timer的s1值在改变), 而普通函数就是指向的window (所以值还是初始时的0)
function Timer() {
this.s1 = 0;
this.s2 = 0;
// 箭头函数
setInterval(() => this.s1++, 1000);
// 普通函数
setInterval(function () {
this.s2++;
}, 1000);
}
var timer = new Timer();
setTimeout(() => console.log('s1: ', timer.s1), 3100); // s1: 3
setTimeout(() => console.log('s2: ', timer.s2), 3100); // s2: 0
//此时的init里的箭头函数就是指向定义时的handler对象, 而doSomething中的普通函数就指向window
var handler = {
id: '123456',
init: function() {
document.addEventListener('click',
event => this.doSomething(event.type), false);
},
doSomething: function(type) {
console.log('Handling ' + type + ' for ' + this.id);
}
};