防止每个订阅运行Observable

时间:2016-03-03 03:44:16

标签: rx-java reactive-programming

由于我的误解,这是一个反应式编程的概念性问题,我认为。

我有Observable发出返回JSON的网络调用,我filter(),查看JSON以获取管理标记,然后在subscribe()方法中执行操作。 / p>

observable
.filter((json) -> { return json.isAdmin; })
.subscribe((json) -> { /* Do things for admin */ });

我也想这样做,但当用户不是管理员时:

observable
.filter((json) -> { return !json.isAdmin; })
.subscribe((json) -> { /* Do things for non-admin */ });

我现在知道如果我运行上面两个代码块,网络调用将被两次调用。

我知道我可以在单subscribe()方法中添加if语句,但我不确定这是否是反应方式。

是否有一种方法可以保持上述结构,但只能将可观察的一次设置为运动 - 即。一个网络电话不是两个?

似乎我想以多种方式对Observable的结果做出反应,而不会使Observable多次运行。

1 个答案:

答案 0 :(得分:2)

有两大类可观察量:hot and cold个。您描述的一个可观察对象,其生成部分在每个subscribe()调用上执行,称为 cold 。另一方面, hot observable通常会发出项目,而不管客户订阅和取消订阅。

对于您的用例,一系列运算符可能适用:connectpublishshare等。

一个例子:

ConnectableObservable</*Your type*/> connectable = Observable.just(1, 2, 3).publish();

connectable
    .filter((json) -> { return json.isAdmin; })
    .subscribe((json) -> { /* Do things for admin */ });

connectable
    .filter((json) -> { return !json.isAdmin; })
    .subscribe((json) -> { /* Do things for non-admin */ });

connectable.connect(); // here's when sharedObservable starts emitting items

有一个beta运算符autoConnect(),当订阅指定数量的客户端时会自动连接到observable:

Observable<Integer> autoObservable = Observable.just(1, 2, 3).publish().autoConnect(2);
autoObservable.subscribe();
autoObservable.subscribe(); // here's when autoObservable starts emitting items

我必须提及经常使用的share()运算符,它是.publish().refCount()的快捷方式。来自它的javadoc:

  

返回一个新的Observable,它可以多播(共享)原始的Observable。只要至少有一个订阅者,此Observable将被订阅并发送数据。当所有订阅者都取消订阅时,它将取消订阅源Observable。

Observable<Integer> shared = Observable.just(1, 2, 3).share();
shared.subscribe(); // starts emitting here...
shared.subscribe(); // ... but is not triggered again, only starts listening for new emissions
// (potential race condition regarding the first emitted item)