背景
Javascript 的 this 是我的心病,多数情况下知道其运行结果,个别变态的场景下,就给不出解释了,昨天一次偶然的机遇让我有兴趣尝试看一看 Javascript 语言规范,一看就悟了。
偶然的机遇就是一篇文章:http://www.cnblogs.com/aaronjs/p/3339107.html,这篇文章中关于 this 的部分我错了1/4。
this
待分析程序
1 var x = 10; 2 var foo = { 3 x: 20, 4 bar: function () { 5 var x = 30; 6 return this.x; 7 } 8 }; 9 10 console.log( 11 foo.bar(), // 1. 12 (foo.bar)(), // 2. 13 (foo.bar = foo.bar)(), // 3. 14 (foo.bar, foo.bar)() // 4. 15 );
先看一个语言规范
Reference Type 规则:
- 是一个内部结构,不能用作变量或属性在值。
- 这个结构包含两部分:base object 和 property name。
- 可以用来解释 this (本文的目的)。
方法调用
方法可以使用 new 调用、使用 apply 调用、使用 call 调用和常规调用,这里我们只解释常规调用。
xxx() 中的 this 指向什么呢?这里得看 xxx 的返回类型是什么,如果是 Reference Type,this 就指向 Reference Type 的 base object,否则就指向 window(根据宿主而定)。
再看一下上面的例子:
1 console.log( 2 foo.bar(), // 1. 3 (foo.bar)(), // 2. 4 (foo.bar = foo.bar)(), // 3. 5 (foo.bar, foo.bar)() // 4. 6 );
1 和 2 返回的是Reference Type,因此输出为 20,3 和 4 返回的是function object,因此输出的是 10。
括号的规范
赋值的规范
逗号的规范
备注
再次印证了一个道理,官方永远是最好的教程。