这个系列的文章尽量每个点都能从一下三个方面来梳理自己的思路:
1、使用场景
2、能解决什么问题
3、怎么解决
先从this来看吧,什么是this?
1、this是js的关键字之一,他是对象 自动生成的一个内部对象,只能在 对象内部使用。随着函数的使用场合的不同,this的值会发生变化;
2、this指向什么,安全取决于什么地方以什么方式调用,而不是创建时。
举个例子吧
var coldMan = {
name = "栗老师",
getName = function({
console.log(this.name)
})
};
var example = coldMan.getName;
example(); // undefined
this并没有按照我们想的指向coldMan,这样也向我们展示了this的指向并不是在函数创建确定的而是在函数调用的时候,接下来就让我们来看看函数调用的时候是怎么来判断this的指向的;
第一种方式:默认绑定
上栗子:
function foo(){
var a = 1;
console.log(this.a); //10
}
var a = 10;
foo()
WFT,居然不是1,是的打印出来的是外面的 a = 10;实际上像这样直接使用的函数,函数内的this指向的是全局变量window;
第二种方式: 隐性绑定
栗子来了
function foo(){
console.log(this.a);
}
var object = {
a : 1,
foo : codeMan
}
foo(); //undefined
object.foo(); // 1
当foo函数执行的时候有了上下文,那么this默认将绑定上下文对象,this即为object,等价于输出object.a;还可以这样理解,函数作为对象的一个属性时,并且作为对象的一个属性被调用的时候,函数的this指向该对象;
总结一下
情况1:如果一个函数中有this,但是它没有被上一级的对象所调用,那么this指向的就是window,这里需要说明的是在js的严格版中this指向的不是window,但是我们这里不探讨严格版的问题,你想了解可以自行上网查找。
情况2:如果一个函数中有this,这个函数有被上一级的对象所调用,那么this指向的就是上一级的对象。
情况3:如果一个函数中有this,这个函数中包含多个对象,尽管这个函数是被最外层的对象所调用,this指向的也只是它上一级的对象,例子3可以证明,如果不相信,那么接下来我们继续看几个例子。
第三种显示绑定
从刚才的栗子中我们可以看出,要使用隐式绑定,那么我们的函数就必须包含于上下文中,那么我们的显示绑定就该出场了
call、apply、bind
这三个函数的作用就是改变函数的this指向
又有栗子了:
function foo(a,b){
console.log(a + b)
}
foo.call(null,'栗','老师'); //栗老师
foo.apply(null,['栗','老师']); //栗老师
apply和call的不同支出在于apply只有两个参数,第一个放 this对象,第二个是以数组的形式放置原函数的参数
而bind函数的用法为:
function foo(){
console.log(this.a);
}
var obj = { a : 10};
foo = foo.bind(obj);
foo(); //10
在这个栗子里,bind的作用是将obj绑定到foo()函数的this上
还有一种就是new 绑定
上代码
function Foo(){
this.name = '栗老师';
this.age = 22;
console.log(this);//Foo {name: '栗老师',age: 22}
}
var f = new Foo();
console.log(f.name);//栗老师
console.log(f.age);//22
如果函数作为构造函数用,那么其中的this就代表它即将new出来的对象。
总结一下
1.如果函数被 new 修饰
this绑定的是新创建的对象,例:var bar = new foo(); 函数 foo 中的 this 就是一个叫foo的新创建的对象 , 然后将这个对象赋给bar , 这样的绑定方式叫 new 绑定 。
2.如果函数是使用 call,apply,bind来调用的
this绑定的是 call,apply,bind 的第一个参数.例: foo.call(obj); , foo 中的 this 就是 obj , 这样的绑定方式叫 显性绑定 .
3.如果函数是在某个 上下文对象 下被调用
this绑定的是那个上下文对象,例 : var obj = { foo : foo }; obj.foo(); foo 中的 this 就是 obj . 这样的绑定方式叫 隐性绑定 .
4.如果都不是,即使用默认绑定
例:function foo(){...} foo() ,foo 中的 this 就是 window.(严格模式下默认绑定到undefined).