我有一个组件从服务中提取内容来处理它。问题是我可以多次调用此函数,这会导致我的数组重复。我有以下解决方法:
getOptions(): Observable<PickQuality[]> {
console.log("MY LENGTH: ", this.options.length) // <=== Always returns 0 because the callback hasn't run yet
if(this.options.length == 0) {
this.championService.getChampions()
.subscribe(champions => {
champions.forEach(champion => this.options.push(new PickQuality(champion, 0)));
this.reevaluate();
this.optionsSubject.next(this.options);
});
return this.optionsSubject.asObservable();
}
else
return Observable.of(this.options);
}
并且它不起作用,然后我在回调中尝试了以下技巧(正确识别this.options.length
):
if(this.options.length != 0) return; // <=== Looks bad!
实际上有效,但对我来说似乎效率极低,因为我的服务调用仍然执行。我该如何解决这个问题?
答案 0 :(得分:1)
我建议稍微重新构建一下代码:
if (this.options.length == 0) {
let source = this.championService.getChampions()
.share();
source.subscribe(champions => {
// ... whatever
this.options = whateverResult;
});
return source;
} else {
return Observable.of(this.options);
}
现在您可以避免使用Subjects并返回代表HTTP请求的源Observable,并通过share()
运算符共享。这意味着只有一个HTTP请求,其结果将发送到此内部subscribe()
调用以及此方法之外的订阅者。
答案 1 :(得分:0)
在推送之前检查重复项。
this.championService.getChampions()
.subscribe(champions => {
champions.forEach(champion => {
if (champions.indexOf(champion) == -1)
this.options.push(new PickQuality(champion, 0));
});
this.reevaluate();
this.optionsSubject.next(this.options);
});