Javascript 在迭代完成之前触发回调
我正在这个项目中使用这个库。一个函数(复制如下)包含用于构建二维阵列的嵌套循环。在数组完全构建之前调用回调。我真的很想了解为什么会发生这种情况,并了解更多关于最佳实践的信息。解决这个问题的最好办法是什么Javascript 在迭代完成之前触发回调,javascript,node.js,Javascript,Node.js,我正在这个项目中使用这个库。一个函数(复制如下)包含用于构建二维阵列的嵌套循环。在数组完全构建之前调用回调。我真的很想了解为什么会发生这种情况,并了解更多关于最佳实践的信息。解决这个问题的最好办法是什么 function getStopTimesForTrips(cb) { timeTable.listOfTripIds.forEach(function(id){ retrieveTimesByTrip(id, function(err, st){
function getStopTimesForTrips(cb) {
timeTable.listOfTripIds.forEach(function(id){
retrieveTimesByTrip(id, function(err, st){
var tempArray = [];
st.forEach(function(st){
tempArray.push(st.arrival_time);
});
timeTable.stopTimes.push(tempArray);
});
});
// cb(null, timeTable); <- This line fires the callback before we finish building the array.
setTimeout(function(){cb(null, timeTable);},2500); // This effective solution is poor form. What's the correct way to solve this issue?
}
函数getStopTimesForTrips(cb){
timeline.listofTripID.forEach(函数(id){
retrieveTimesByTrip(id,函数(err,st){
var tempArray=[];
st.forEach(功能(st){
tempArray.push(圣到达时间);
});
时间表。停车时间。推送(临时数组);
});
});
//cb(null,timeline);一种方法是只使用本机承诺并等待异步调用完成
function getStopTimesForTrips(cb) {
var promises = timeTable.listOfTripIds.map(function(id) {
return new Promise(function(resolve, reject) {
retrieveTimesByTrip(id, function(err, st) {
if (err) return reject();
timeTable.stopTimes = st.map(function(item) {
return item.arrival_time;
}));
resolve();
});
});
});
Promise.all(promises).then(function() {
cb(null, timeTable);
});
}
只需将整个函数设置为表就更好了
function getStopTimesForTrips() {
return Promise.all(
timeTable.listOfTripIds.map(function(id) {
return new Promise(function(resolve, reject) {
retrieveTimesByTrip(id, function(err, st) {
if (err) return reject();
resolve(
st.map(function(item) {
return item.arrival_time;
})
);
});
});
})
);
}
getStopTimesForTrips().then(function(arrival_times) { ... })
您似乎没有使用
async
库中的任何函数。正确的解决方案是使用async
:
async.each(timeTable.listOfTripIds,function(id,cb2){
retrieveTimesByTrip(id, function(err, st){
var tempArray = [];
st.forEach(function(st){
tempArray.push(st.arrival_time);
});
timeTable.stopTimes.push(tempArray);
cb2(err); // Need to call this to tell async this iteration
// is done. Think of it as an async "return".
});
},function(err){
// if we're here it means the `async.each` is done:
cb(null, timeTable);
});
您甚至没有使用库提供的
async
方法。看起来像是一个异步函数的循环,但您可以在不等待所有函数都被调用的情况下调用回调函数。谢谢!这正是我要找的。