规则套用优先顺序:箭头函数->4->3->2->1
1)预设绑定(default binding):没有使用bind,call,apply或new,预设全域物件,在浏览器底下是window
2)隐含绑定(implicit binding):当函数为物件的方法时,在执行阶段this就会被绑定至该物件.
注:只有最顶层的物件才是有用的
3)显示绑定(explicit binding):使用call,bind,apply明确指出要给定this的物件,将第一个参数设定为函数内的context,意即设定第一个参数为函数内this 的值.
call将参数一一传入,apply将参数使用阵列传入,bind在执行函数前,绑定要指定的物件,这样this就会是这个物件
硬绑定(hard binding):指使用bind写死要绑定的物件,可避免函数呼叫时退回到预设绑定
4)new绑定(new binding):this会指向new出来的物件
this的使用场合:
this总是返回一个对象(返回属性或方法"当前"所在的对象)
对象的属性可以赋给另一个对象,所以属性所在的当前对象是可变的,即this的指向是可变的
任何函数本质上都是通过某个对象调用的,如果没有直接指定就是window对象
1)如果一个函数在全局环境中运行,那么this就是指顶层对象(浏览器中为window对象)
可以近似的认为:this是所有函数运行时的一个隐藏参数,指向函数的运行环境.
2)构造函数中的this,指的是实例对象
3)对象的方法
this的指向,是在函数被调用的时候确定的
this取决于调用,而非定义
_**调用指的是所在函数的调用**_
箭头函数不绑定this属性,this的绑定和定义的位置没有任何关系,和调用方式及调用位置有关系
函数执行时所在的作用域,是定义时的作用域,而不是调用时所在的作用域.
call/bind/apply的用法:改变函数体内的this的指向.
function call([thisobj[,arg1[,arg2[,[...argN]]]]):
定义:调用一个对象的一个方法,以另一个对象替换当前对象
call方法传入的第一个参数,始终代表this的指向
apply:apply(thisobj[,argArray])
定义:应用某一对象的方法,用另一个对象替换当前对象
thisobj不传,或传null,undefined,this指向window对象.
test.call(this,arg1,arg2)和test.apply(this,[arg1,arg2]):
作用完全一样,只是接受参数的方式不太一样,
this是你想指定的上下文,可以是任何一个javascript对象.
bind:创建一个函数,然后在需要调用时再执行函数,并非是立即执行函数.
而call,apply是在改变了上下文的this指向后并立即执行函数.
三者传入的第一个参数都是传递this的指向的,也就是对上下文的指定,都可以传入多个参数,
call和bind的后续参数都是按照顺序传参,apply传参类型是数组,
bind的参数可以在函数执行的时候再次添加
总结:
1. 沿着作用域向上找最近的一个function( 不是箭头函数),看这个function最终是怎样执行的。
2. this的指向取决于所属function的调用方式,而不是定义。
3. function调用一般分为以下几种情况:
1)作为函数调用,即:‘foo()'
指向全局对象(globalThis),注意严格模式下是undefined
2)作为方法调用,即:’foo.bar()'/'foo.bar.baz()'/'foo['baz']'/'foo0'
指向最终调用这个方法的对象
3)作为构造函数调用,即:‘new Foo()'
指向一个新对象’Foo {}'
4)特殊调用:即:‘foo.call()'/'foo.apply()'/'foo.bind()'
参数指定成员
4.找不到所属的function,就是全局对象