也许这是一个普遍的问题,我需要一个解决方案来解决我的问题:由于javascript的非阻塞方面,我找不到如何在for循环中执行所有迭代的函数,这里是我的例如,
var text_list=[]
for (var i = 0; i < 10; i++) {
var element = array[index];
tesseract.process("img"+i+".jpg", options, function (err, text) {
if (err) {
return console.log("An error occured: ", err);
}
text_list.push(text)
});
}
console.log(text_list) //
结果好像我这样做:
tesseract.process("img"+9+".jpg"...
tesseract.process("img"+9+".jpg"...
tesseract.process("img"+9+".jpg"...
.
.
.
我需要的是:
tesseract.process("img"+0+".jpg"...
tesseract.process("img"+1+".jpg"...
tesseract.process("img"+2+".jpg"...
.
.
.
答案 0 :(得分:2)
您的问题并没有真正解释您获得的结果,而您的代码似乎缺少代码部分。所以,我能真正帮助的是一般地解释(尽可能使用你的代码)如何解决这类问题。
如果您最终得到的结果都是在循环中引用i
的最后一个值,那么您可能尝试在异步回调中引用i
,但因为回调是稍后调用,for
循环在回调执行之前就已经完成了很久。因此,i
的值位于for
循环中的最后一个值。但是,您的问题实际上并未显示执行此操作的代码,因此这只是基于您描述的有限结果的猜测。要解决此类问题,请确保为循环的每次迭代分别跟踪i
。有很多方法可以做到这一点。在ES6中,在let
循环定义中使用for
将为您解决整个问题。也可以构造一个闭包,使用.forEach()
等......
使用循环进行异步操作需要额外的工作和编码来处理。现代的解决方案是将您的异步操作转换为使用promises,然后使用Promise.all()
等功能来告诉您何时完成所有异步操作并按顺序保存结果。
您也可以手动编码而无需承诺。这是一个手册版本:
const len = 10;
let text_list = new Array(10);
let doneCnt = 0;
let errFlag = false;
// using let here so each invocation of the loop gets its own value of i
for (let i = 0; i < len; i++) {
tesseract.process("img"+i+".jpg", options, function (err, text) {
if (err) {
console.log("An error occured: ", err);
// make sure err is wrapped in error object
// so you can tell errors in text_list array from values
if (!(err instanceof Error)) {
err = new Error(err);
}
text_list[i] = err;
errFlag = true;
} else {
text_list[i] = text;
}
// see if we're done with all the requests
if (++doneCnt === len) {
if (errFlag) {
// deal with situation where there were some errors
} else {
// put code here to process finished text_list array
}
}
});
}
// you can't process results here because async operations are not
// done yet when code here runs
或者,使用promises,你可以制作一个&#34; promisified&#34;版本tesseract.process()
,然后使用promise功能跟踪多个异步操作:
// make promisified version of tesseract.process()
tesseract.processP = function(img, options) {
return new Promise(function(resolve, reject) {
tesseract.process(img, options, function(err, text) {
if (err) {
reject(err)
} else {
resolve(text);
}
});
});
}
const len = 10;
let promises = [];
for (let i = 0; i < len; i++) {
promises.push(tesseract.processP("img"+i+".jpg", options));
}
Promise.all(promises).then(function(results) {
// process results array here (in order)
}).catch(function(err) {
// handle error here
});