在节点jsclosures不按预期工作
我有这段代码:
var responses = []; for( var i=0; i < Number(process.argv[2]); i++) { responses.push(function () { var index = i; function bar() { console.log(index); } return bar; }()); } responses.forEach(function(d){ d(); });
通过使用临时variablesindex
来创build闭包。 如预期的那样输出0 1
,打印我要在闭包中捕获的值。
与http get callback类似的代码不起作用。
var http = require("http"); var urls = ["http://yahoo.com","http://google.com"]; for( var i=0; i < urls.length; i++) { http.get( urls[i] , function(res) { var j = i; res.setEncoding('utf-8'); res.on("data", function(d) { console.log(j); }); }); }
此代码输出: 2 2
我错过了什么?
var j = i;
会在第一个响应中设置数组的长度i
的值,这就是每次login时得到2
的原因。
调用一个匿名函数作为http.get
的第二个参数,它将返回内部函数来处理响应,并且还会记住它所创build的环境。 通过论证的价值i
会在那里留在内存中以后使用。
尝试这个:
var http = require("http"); var urls = ["http://yahoo.com", "http://google.com"]; for (var i = 0; i < urls.length; i++) { http.get(urls[i], (function(i) { return function(res) { res.setEncoding('utf-8'); res.on("data", function(d) { console.log(i); }); } })(i)); }
在javascript(es5)中没有块范围。 所以你使用的for循环不会做的伎俩,而是尝试:
urls.forEach(function(url, i){ http.get( url , function(res) { res.setEncoding('utf-8'); res.on("data", function(d) { console.log(i); }); });