使用RXJava 2,我正在尝试创建一个异步事件总线。
我有一个单独的对象,具有PublishSubject
属性。发射器可以使用onNext
在主题上向总线发送事件。
如果订阅者执行任务很长,我希望我的总线在多个线程上调度任务以同时执行任务。这意味着我希望在项目发布后立即开始项目的工作,即使前一项目的工作没有完成。
但是,即使将observeOn
与scheduler
一起使用,我也无法同时运行我的任务。
示例代码:
public void test() throws Exception {
Subject<Integer> busSubject = PublishSubject.<Integer>create().toSerialized();
busSubject.observeOn(Schedulers.computation())
.subscribe(new LongTaskConsumer());
for (int i = 1; i < 5; i++) {
System.out.println(i + " - event");
busSubject.onNext(i);
Thread.sleep(1000);
}
Thread.sleep(1000);
}
private static class LongTaskConsumer implements Consumer<Integer> {
@Override
public void accept(Integer i) throws Exception {
System.out.println(i + " - start work");
System.out.println(i + " - computation on thread " + Thread.currentThread().getName());
Thread.sleep(2000);
System.out.println(i + " - end work");
}
}
打印:
1 - event
1 - start work
1 - computation on thread RxComputationThreadPool-1
2 - event
3 - event
1 - end work
2 - start work
2 - computation on thread RxComputationThreadPool-1
4 - event
2 - end work
3 - start work
3 - computation on thread RxComputationThreadPool-1
3 - end work
4 - start work
4 - computation on thread RxComputationThreadPool-1
4 - end work
这意味着第2项的工作等待第1项的工作结束,即使事件2已经发出。
答案 0 :(得分:1)
当下面的调用发生时,将从Schedulers.computation()
创建一个工作程序,并将其用于整个流。这就是为什么您提交的所有工作都是在RxComputationThreadPool-1
上完成的。
busSubject.observeOn(Schedulers.computation())
.subscribe(new LongTaskConsumer());
安排多线程的工作:
busSubject.flatMap(x ->
Flowable.just(x)
.subscribeOn(Schedulers.computation()
.doOnNext(somethingIntensive))
.subscribe(new LongTaskConsumer());
另请注意,密集型工作是在flatMap
内而非LongTaskConsumer
内执行的,因为所有项目都会连续到达LongTaskConsumer
。
还有其他一些并行工作的方法,您可能需要根据PublishSubject
发生的事件数进行调查。