如何将 Observable 转换为 ReplaySubject?

Posted

技术标签:

【中文标题】如何将 Observable 转换为 ReplaySubject?【英文标题】:How to convert an Observable to a ReplaySubject? 【发布时间】:2017-06-03 11:42:52 【问题描述】:

这是我现在正在做的将Observable 转换为ReplaySubject

const subject = new Rx.ReplaySubject(1);

observable.subscribe(e => subject.next(e));

这是进行转换的最佳方式,还是有更惯用的方式?

【问题讨论】:

如果你真的想剃掉字符,我想你可以做observable.subscribe(subject.next)。但是,如果你有 observable,为什么还需要创建主题呢?如果您只想要回放功能,请使用Observable.replay 方法。 实际上你甚至可以做observable.subscribe(subject),没有.next) 只需注意一旦observable完成,主题也会完成。 @jonrsharpe Observable.replay 在 RxJS v5 中似乎不可用。 对于 RxJS 版本 6.4.0,这可以解决问题:observable.pipe(shareReplay(1)),相当于(从 6.4.0 开始)observable.pipe(shareReplay( bufferSize: 1, refCount: false ))。有关refcount 的血腥细节请看这里:blog.angularindepth.com/… 以上shareReplay评论的文档learnrxjs.io/operators/multicasting/sharereplay.html 【参考方案1】:

如果您想传递所有 3 种类型的通知,您可以只使用 observable.subscribe(subject),因为 Subject 已经表现得像观察者。例如:

let subject = new ReplaySubject();
subject.subscribe(
  val => console.log(val),
  undefined, 
  () => console.log('completed')
);

Observable
  .interval(500)
  .take(5)
  .subscribe(subject);

setTimeout(() => 
  subject.next('Hello');
, 1000)

观看现场演示:https://jsbin.com/bayewo/2/edit?js,console

然而,这有一个重要的后果。由于您已经订阅了源 Observable,因此您将其从“冷”变为“热”(也许在您的用例中并不重要)。

【讨论】:

【参考方案2】:

和第一个答案一样,主体也是观察者。

const subject = new Rx.ReplaySubject(1);
observable.subscribe(subject);

【讨论】:

【参考方案3】:

这取决于你所说的“转换”是什么意思。

如果您需要共享您的 observable 并重放这些值,请使用 observable.pipe(shareReplay(1))

如果您还想拥有订阅者功能,则需要使用订阅原始 Observable observable.subscribe(subject); 的 ReplaySubject。

【讨论】:

以上是关于如何将 Observable 转换为 ReplaySubject?的主要内容,如果未能解决你的问题,请参考以下文章

如何将 RxSwift 的 Single 转换为 Observable 并忽略“完成”事件?

RxJS:如何将 Observable<Observable<Thing>> 转换为 Observable<Thing[]>

如何以角度将 JSON 对象数组转换为 Observable 数组

Dart:将 Observable 转换为 Future,反之亦然?

Angular 2:将 Observable 转换为 Promise

无法将“Observable<Data>”类型的值转换为预期的参数类型“Data”