如何在Observable流(RxJava)中以不同方式处理每个项目

时间:2016-03-24 10:55:11

标签: java functional-programming rx-java

让我举一个例子:给定从1到10的数字流,处理偶数和奇数不同。在不同的线程中处理奇数并将此变换应用于它们(2 * i)。在主线程中处理偶数并将此转换应用于它们(2 * i - 1)。订户如下:

finalObservable.subscribe(new Action1<Integer>() {
   @Override
   public void call(Integer t) {
      System.out.println(Thread.currentThread() + " " + t);
   }});

输出应为

Thread-1 2
main 3
Thread-1 6
main 7
Thread-1 10
main 11
Thread-1 14
main 15
Thread-1 18
main 19

如何使用RxJava-Observables运算符执行此操作?

2 个答案:

答案 0 :(得分:2)

处理此问题的最佳方法是使用share()的{​​{1}}运算符。在huuuuge简化中,您可以将Observable分成多个。{1}}。因此,在您的情况下,表示数字流的可观察对象可以分为两个可观察对象。一个用于奇数,一个用于偶数。

假设observable(在您的示例中为allNumbers)表示&lt; 1,10&gt;数字流:

finalObservable

简化了Retrolambda:

final Observable<Integer> allNumbers =
        Observable.from(new Integer[]{1, 2, 3, 4, 5, 6, 7, 8, 9, 10})
                .share();
Observable<Integer> oddNumbers = allNumbers.filter(new Func1<Integer, Boolean>() {
    @Override
    public Boolean call(Integer integer) {
        return integer % 2 != 0;
    }
});
Observable<Integer> evenNumbers = allNumbers.filter(new Func1<Integer, Boolean>() {
    @Override
    public Boolean call(Integer integer) {
        return integer % 2 == 0;
    }
});

final Action1<Integer> printingAction = new Action1<Integer>() {
    @Override
    public void call(Integer t) {
        System.out.println(Thread.currentThread() + " " + t);
    }
};

evenNumbers.subscribeOn(Schedulers.computation()).subscribe(printingAction);
oddNumbers.subscribeOn(AndroidSchedulers.mainThread()).subscribe(printingAction);

您没有在哪个线程中指定完全需要处理的内容,因此您可能需要更正final Observable<Integer> allNumbers = Observable.from(new Integer[]{1, 2, 3, 4, 5, 6, 7, 8, 9, 10}) .share(); Observable<Integer> oddNumbers = allNumbers.filter(integer -> integer % 2 != 0); Observable<Integer> evenNumbers = allNumbers.filter(integer -> integer % 2 == 0); final Action1<Integer> printingAction = t -> System.out.println(Thread.currentThread() + " " + t); evenNumbers.subscribeOn(Schedulers.computation()).subscribe(printingAction); oddNumbers.subscribeOn(AndroidSchedulers.mainThread()).subscribe(printingAction); 个参数并添加subscribeOn个运算符。根据您的需要。

答案 1 :(得分:0)

一般的想法是这样的(使用flatMap):

Observable.from(new Integer[]{1, 2, 3, 4, 5})
          .flatMap(number -> {
              if (number % 2 == 0) {
                  return Observable.just(2 * number - 1);
              } else {
                  return Observable.fromCallable(() -> 2 * number)
                                   .subscribeOn(Schedulers.io());
              }
          })
          .subscribe(new Action1<Integer>() {
              @Override
              public void call(Integer integer) {
                  System.out.println(Thread.currentThread() + " " + integer);
              }
          });