对于箭头函数里的this
先说总结:
- 箭头函数没有本人的this、arguments,箭头函数里的this用的是parent作用域的this。
- 箭头函数里的this是词法作用域,是由代码构造决定的,跟在哪里调用无关,与箭头函数在代码里的地位无关。
- 确定箭头函数里this的指向,能够动态剖析代码构造,始终往上找function,如果有,就是最近的function里的this,如果到最外层都没有,就是window。
- 箭头函数的this,一旦确定后是不可更改的。
记住,箭头函数里的this是能够动态剖析的,然而函数里的this又齐全不一样了
上面开始注释
箭头函数没有本人的this、arguments,箭头函数里的this用的是parent作用域的this。
廖雪峰的文章说,箭头函数里的this是词法作用域。
那么就是由代码构造决定的,跟在哪里调用无关,事实证明也是这样的。
箭头函数呈现的地位有两种:
- 在对象里
- 在函数里
箭头函数在对象里
var obj = { param: 123, ff : () => console.log(this), // window, strict模式下是undefined}
因为箭头函数没有本人的this,会去找parent的this,然而对象不形成独自的作用域,没有词法作用域,所以持续往上找parent,就找到了全局作用域。
通过babel编译,发现间接就把this替换成了undefined
// bebal编译后的后果// void 0就是undefined"use strict";var _this = void 0;var obj = { param: 123, ff: function ff() { return console.log(_this); } };
箭头函数在函数里
function test () { let param = 5656; let ff = () => console.log(this);}
箭头函数的this是词法作用域,词法作用域是跟代码构造相干的,那么是能够动态剖析的。
因为是词法作用域,那么箭头函数里的this跟在哪里调用无关,与箭头函数在代码里的地位无关。
咱们剖析一下,箭头函数没有本人的this,会找parent的this,它的parent的是test函数,函数是有作用域的,有词法作用域,所以test里的this就是箭头函数的this。
也就是箭头函数里的this,通过动态剖析,会始终往上找function,找到了,就用最近的function里的this,找不到,就用window。
通过babel编译一下,发现箭头函数的this即是test函数里的this:
"use strict";function test() { var _this = this; var param = 5656; var ff = function ff() { return console.log(_this); // 这里的this取的是test函数的this };}
因为箭头函数和test函数的this是一样的,那么如果test函数里的this变动了,那么箭头函数的this也会跟着变动。比方看这个例子:
let obj = { param: 123, ff: function () { let rr = () => console.log(this); rr(); }}obj.ff(); // obj , 因为这时ff函数里的this是obj对象let tt = obj.ff;tt(); // window ,因为这时ff函数里的this是全局对象
这个通过babel编译后的后果是:
"use strict";var obj = { param: 123, ff: function ff() { var _this = this; var rr = function rr() { return console.log(_this); }; rr(); }};obj.ff();var tt = obj.ff;tt();
留神,箭头函数的this,一旦确定后是不可更改的
这句的了解是:箭头函数的this一旦确定,就不能更改了,典型的如在setTimeout
函数里用箭头函数。要辨别下面的状况,箭头函数rr
的this取的是ff
函数的this,然而ff
函数的this是没有确定的,运行起来后ff
函数的this才确定。
function test () { return () => console.log(this);}let obj = { aa: 123,}let rr = test.call(obj);setTimeout(rr,1000); // obj ,而不是window 因为箭头函数rr的this曾经确定了,前面不能更改
多层嵌套的状况
let obj = { ff1: function () { let obj2 = { ff2: () => console.log(this), obj3: new Object(() => console.log(this)) }; return obj2; }, fun1: function (){ return function fun2(){ return function fun3(){ return () => console.log(this); } } }}obj.ff1().ff2(); // obj, 取的ff1的thisobj.fun1()()()(); // window,取的fun3的this,因为嵌套函数的this不能继承,所以是window
箭头函数ff2
里的this,向上找parent,obj2是对象没有作用域,持续向上,找到ff1
函数,于是箭头函数ff2
的this就是取ff1
函数的this。obj3的new Object()的传参是箭头函数,外面的this实用的规定也一样,也是始终向上找parent,最初是ff1
函数的this,看babel的转换的代码就晓得了。
"use strict";var obj = { ff1: function ff1() { var _this = this; var obj2 = { ff2: function ff2() { return console.log(_this); }, obj3: new Object(function () { return console.log(_this); // 取的是ff1的this }) }; return obj2; }, fun1: function fun1() { return function fun2() { return function fun3() { var _this2 = this; return function () { return console.log(_this2); }; }; }; }};obj.ff1().ff2(); // obj, 取的ff1的thisobj.fun1()()()(); //
总结
- 箭头函数没有本人的this、arguments,箭头函数里的this用的是parent作用域的this。
- 箭头函数里的this是词法作用域,是由代码构造决定的,跟在哪里调用无关,与箭头函数在代码里的地位无关。
- 确定箭头函数里this的指向,是动态剖析代码构造,始终往上找function,如果有,就是最近的function里的this,如果到最外层都没有,就是window。
- 箭头函数的this,一旦确定后是不可更改的。
记住,箭头函数里的this是能够动态剖析的,然而函数里的this又齐全不一样了