参考 http://www.educity.cn/wenda/54753.html
已实验验证结果正确。
1、下列哪些正确?(B、C)A.function(){alert("Here!");}();B.(function(){alert("Here!");})();C.(function(){alert("Here!");}());
下面也已经实验验证结果正确。
2、下列哪个结果是正确的?(A、B、C、D)A.(function(a1,a2){alert("Here!"+(a1+a2));})(1,2);B.(function(a1,a2){alert("Here!" +(a1+a2));}(1,2));C.void function(a1,a2){alert("Here!" +(a1+a2));}(1,2);D.var f = function(a1,a2){alert("Here!" +(a1+a2));}(1,2);注:A 、B、C与D四种格式都正确,前两者属于同种情况的不同写法,后两种是将函数对象的返回值赋给其他变量,C是忽略函数返回值,而D正相反!
下面这个的结果也验证,但是注意,稍稍改一下,效果就很大差别。
function Foo() {var a = 123;this.a = 456;(function() {console.log(a); // 123console.log(this.a); // undefined })(); }; var f = new Foo();结果: 123 undefined(1)匿名函数可以直接访问到外层署名函数(Foo)中的变量(使用关键字var定义的),但不能访问外层署名函数的属性(使用关键字this定义的);
稍微改一下,把Foo前面的new去掉,直接调用Foo,如下:
function Foo() {var a = 123;this.a = 456;(function() {console.log(a); // 123console.log(this.a); // undefined })(); }; var f = Foo();结果: 123 456
然后在最后分别加上console.log(f)看看f被赋予什么内容:
var f = new Foo(); console.log(f);结果: Foo { a: 456 }var f = Foo(); console.log(f);结果: undefined
开始写自己代码的时候,发现了下面的情况。本来以为是node跟原生js的区别呢,看来不是。
/*** Created by baidu on 16/10/24.*/ function test(){var a = 123;this.a = 456;return (function(p1,p2){console.log(a);console.log(this.a);return p1+p2;})(1,2); }; (function(){console.log(test()); }());用node跑: 123 456 3
内部要访问数据,可以通过传参数(方法一):
function Foo() {var a = 123;this.a = 456;(function(_this) {console.log(a); // 123console.log(_this.a); // 456})(this); }; var f = new Foo();结果: 123 456
另外,注意下面这种情况:
(function() {var a = 123;this.a = 456;(function() {console.log(a); // 123console.log(this.a); // 456 })(); })();结果: 123 456(1) 匿名函数既可以直接访问外层匿名函数中的变量,又直接可以访问外层匿名函数中的属性,而匿名函数却不可以直接访问外层已命名函数中的属性;
访问没有定义过的this.xxx,也是很有意思的:
/*** Created by baidu on 16/10/24.*/function Foo() {var a = 123;this.a = 456;(function() {console.log(a); // 123console.log(this.a); // undefinedthis.b = 789;})();(function() {console.log(this.b); // 789 })(); }; var f = new Foo(); (function() {console.log(this.a); // undefinedconsole.log(this.b); // 789 })();
结果:
123
undefined
789
undefined
789
后面分析。
再来一个里外都是匿名函数的情况:
/*** Created by baidu on 16/10/24.*/(function() {var a = 123;this.a = 456;(function() {console.log(a); // 123console.log(this.a); // 456this.b = 789;})();(function() {console.log(this.b); // 789 })(); })(); (function() {console.log(this.a); // 456console.log(this.b); // 789 })();结果: 123 456 789 456 789
通过上面两个例子的对比及分析,可以看出如下结论:
(1)匿名函数(即用两个小括号括起来的部分)位于一个执行上下文,不论这些代码放在哪个位置上。
再比较下面两种情况:
情况1:
function Foo() {(function() {this.b = 789;})();(function() {console.log(this.b); // 789console.log(b); // 789var a = 0;console.log(a); // 0 })(); } var f = new Foo(); (function() {console.log(this.b); // 789console.log(b); // 789 })();结果: 789 789 0 789 789
情况2:
/*** Created by baidu on 16/10/24.*/function Foo() {(function() {this.b = 789;})();(function() {console.log(this.b); // 789console.log(b); //undefinedvar b = 0;console.log(b); // 0 })(); } var f = new Foo(); (function() {console.log(this.b); // 789console.log(b); // 789 })();结果: 789 undefined 0 789 789
从以上对比,可以看出:
没有加 this取值时,如果当前 {} 中不存在同名的局部变量,则等同于加 this 处理;如果当前 {} 中存在同名的局部变量,则按常规处理。
上面第二例中,b会打印出undefined,是因为在{}出现了b,并且是在后面出现的,当前还是undefined.
以上,是一些实验结果。