首先,我知道这已经被回答过很多次了,但是我一直无法找到如何针对这种特定情况实现它。
一方面,我有一种与此类似的方法
getSomeInfoFromAnApi(param1: number, param2: number): Observable<any> {
// Call some REST API and return an Observable
}
另一方面,该方法将以这种方式在其他地方调用:
data.forEach(graphic =>
graphic.series.forEach(serie => {
if (serie.channelValueType === 'string') {
this.myService.getSomeInfoFromAnApi(graphic.modelId, serie.channelId).subscribe(myResponse => {
// this is much more complex, just keeping it small for the sake of the example
// but the important thing here is that a member of the 'serie' item is being modified
serie.points = myResponse;
});
}
})
);
// graphics$ is defined as a BehaviorSubject
this.graphics$.next(data);
这里的问题是对BehaviorSubject的next的调用发生的时间比应该发生的要早得多,因为getSomeInfoFromAnApi是一个异步调用。
确保调用仅在处理完数据集合中的所有元素之后才发生的最佳方法是什么,这意味着对getSomeInfoFromAnApi的所有可能的调用都已响应并执行了预订的代码。
初始方法
根据我在stackoverflow上找到的一些答案,这是我到目前为止已经实现的方法,但是我敢肯定必须有一个更好的方法:
data.forEach((graphic, dataIndex) =>
graphic.series.forEach((serie, seriesIndex) => {
if (serie.channelValueType === 'string') {
this.myService.getSomeInfoFromAnApi(graphic.modelId, serie.channelId).subscribe(myResponse => {
// this is much more complex, just keeping it small for the sake of the example
// but the important thing here is that a member of the 'serie' item is being modified
serie.points = myResponse;
if(data.length === dataIndex + 1 && graphic.series.length === seriesIndex + 1) {
this.graphics$.next(data);
}
});
}
else {
if(data.length === dataIndex + 1 && graphic.series.length === seriesIndex + 1) {
this.graphics$.next(data);
}
}
})
我认为类似这样的方法可能会适合您的情况。
除了使用BehaviorSubject并手动将其发送到该流中之外,我们还可以根据您的data
使用创建一个流,from()
以分别发出数组项,用于mergeMap()
处理订阅您的api调用,然后用于toArray()
在所有调用完成后将所有结果合并到一个数组中完成。
graphics$ = from(data).pipe(
mergeMap(graphic => from(graphic.series).pipe(
filter(series => series.channelValueType === 'string'),
mergeMap(series => this.myService.getSomeInfoFromAnApi(graphic.modelId, series.channelId).pipe(
map(myResponse => ({...series, points: myResponse}))
),
),
toArray()
)
本文收集自互联网,转载请注明来源。
如有侵权,请联系 [email protected] 删除。
我来说两句