所有这些代码都在一个名为juggling_async.js的文件中。这是node school的练习9。
这个代码坏了(我写的):
var http = require('http');
var bl = require('bl');
var result = [];
var count = 0;
for(var i=0;i<3;i++) {
http.get(process.argv[2 + i], function(res){
res.pipe(bl(function(err,data){
if(err) return console.log(err.message);
result[i] = data.toString();
count++;
if(count == 3) {
for(var j=0;j<result.length;j++) {
console.log(result[j]);
}
}
}));
});
}
它注销:"未定义"
"未定义"
"未定义"
"[这是一个字符串]"
这个代码解决了问题:
var http = require('http')
var bl = require('bl')
var results = []
var count = 0
function printResults () {
for (var i = 0; i < 3; i++)
console.log(results[i])
}
function httpGet (index) {
http.get(process.argv[2 + index], function (response) {
response.pipe(bl(function (err, data) {
if (err)
return console.error(err)
results[index] = data.toString()
count++
if (count == 3) // yay! we are the last one!
printResults()
}))
})
}
for (var i = 0; i < 3; i++)
httpGet(i)
在我看来,我的坏代码应该可以工作。我开始循环I,从0开始,我使用http库发出http.get请求,http.get进行回调,其中res是http.get要求的响应。函数(res)是在get请求返回之前不会运行的回调,对吗?此时,我仍然为0,所以我将data.toString()设置为result[0],对吗?结果数组的第一个元素应该包含正确的内容,而不是未定义的?
很明显,我的思想和代码都崩溃了。我错了该怎么办?
BTW:我读了关于闭包的相关帖子,我仍然不明白为什么我的代码被破坏了,或者它在哪里失败了。
在第一个例子中,变量i
是一个引用,因此循环以i为最大值结束,然后调用所有回调并使用引用i,该引用将被设置为与for循环结束时相同的状态。
在第二个例子中,计数被保存到闭包中的另一个变量中。